跳到主要内容
极客日志极客日志面向AI+效率的开发者社区
首页博客GitHub 精选镜像工具UI配色美学隐私政策关于联系
搜索内容 / 工具 / 仓库 / 镜像...⌘K搜索
注册
博客列表
C++算法

栈的压入弹出序列判断算法详解

栈的压入弹出序列验证依赖模拟栈操作过程。核心在于利用辅助栈模拟入栈动作,并在每次入栈后检查栈顶元素是否匹配当前期望弹出的元素,若匹配则持续出栈。最终通过判断辅助栈是否为空来确定序列是否有效。该算法时间复杂度为 O(n),空间复杂度为 O(n),适用于 C++ 等支持标准库容器语言的场景。边界情况包括空序列和长度不一致的处理。

山野来信发布于 2026/3/15更新于 2026/6/1420 浏览
栈的压入弹出序列判断算法详解

问题描述

给定两个整数序列:

  • pushV:压栈序列
  • popV:待验证的弹栈序列

需要判断 popV 是否可能是 pushV 对应的弹栈序列。

核心思路

要解决这个问题,关键在于理解栈的后进先出特性。我们可以通过模拟整个压栈弹栈过程来验证序列的合法性。

具体规则如下:

  • 压栈操作:元素按照 pushV 的顺序依次入栈
  • 弹栈操作:在任意时刻,只能弹出栈顶元素
  • 时机选择:可以在压入任意元素后选择弹出栈顶元素

关键洞察是:每当栈顶元素与当前期望弹出的元素匹配时,就立即弹出。这是一种贪心策略,因为如果此时不弹出,后续再想弹出这个元素就必须先把新压入的元素弹出来,这往往会导致顺序错乱。

完整代码实现

#include <vector>
#include <stack>

using namespace std;

class Solution {
public:
    bool IsPopOrder(vector<int>& pushV, vector<int>& popV) {
        // 使用辅助栈模拟压栈弹栈过程
        stack<int> st;
        // 双指针:_push 指向当前要压入的元素,_pop 指向当前要弹出的元素
        size_t _push = 0; // 压栈序列的索引
        size_t _pop = 0;  // 弹栈序列的索引

        // 遍历所有需要压入的元素
        while (_push < pushV.size()) {
            // 将当前元素压入栈中
            st.push(pushV[_push++]);
            
            // 检查栈顶元素是否与当前期望弹出的元素匹配
            // 如果匹配,则连续弹出所有匹配的元素
             (!st.() && st.() == popV[_pop]) {
                _pop++; 
                st.(); 
            }
        }

        
         st.();
    }
};
while
empty
top
// 移动弹栈序列指针
pop
// 弹出栈顶元素
// 如果所有元素都能正确弹出,栈应该为空
return
empty

算法步骤详解

让我们通过一个具体例子来理解算法的执行过程:

示例输入:

  • pushV = [1, 2, 3, 4, 5]
  • popV = [4, 5, 3, 2, 1]
执行流程演示

初始状态下,辅助栈为空,指针 _push 指向 1,_pop 指向 4。

  1. 压入阶段:依次将 1、2、3 压入栈中。此时栈内为 [1, 2, 3],栈顶 3 不等于期望值 4,继续压入。
  2. 匹配弹出:压入 4 后,栈顶变为 4,与期望值匹配。执行弹出操作,栈变为 [1, 2, 3],_pop 指针移向 5。
  3. 连续弹出:接着压入 5,栈顶为 5,匹配期望值 5,弹出。随后栈顶变为 3,匹配期望值 3,弹出。依此类推,直到栈内元素全部按序弹出。

最终栈为空,说明序列合法,返回 true。

复杂度分析

时间复杂度

主循环遍历 pushV 中的每个元素一次。内层循环虽然嵌套,但每个元素最多被压入和弹出各一次。因此总时间复杂度为 O(n),其中 n 为序列长度。

空间复杂度

需要一个辅助栈来存储元素,最坏情况下需要存储所有 n 个元素。总空间复杂度为 O(n)。

边界情况处理

在实际编码中,需要注意以下边界条件:

  1. 长度不一致:如果两个序列长度不同,直接返回 false。
  2. 空序列:如果两个序列都为空,视为匹配,返回 true。
  3. 单元素序列:需确保唯一元素匹配成功。

总结

这道题的核心在于利用辅助栈模拟实际过程,并结合双指针技巧跟踪进度。这种模拟法不仅适用于栈的相关问题,在很多其他算法场景中也有广泛应用。掌握这种思维方式,对于提升算法设计能力具有重要意义。


参考资料:

  • LeetCode 946. 验证栈序列
  • 数据结构与算法 - 栈的应用

目录

  1. 问题描述
  2. 核心思路
  3. 完整代码实现
  4. 算法步骤详解
  5. 执行流程演示
  6. 复杂度分析
  7. 时间复杂度
  8. 空间复杂度
  9. 边界情况处理
  10. 总结
  • 免费图片AI生成工具免费生成了解详情
  • Magick API 一键接入全球大模型注册送1000万token查看
  • 免费图片视频在线生成30秒,将你的创意变成现实开始设计
  • X/Twitter免费视频下载器免登陆无限额度免费视频解析下载了解详情
  • 100+免费在线小游戏爽一把
极客日志微信公众号二维码

微信扫一扫,关注极客日志

微信公众号「极客日志V2」,在微信中扫描左侧二维码关注。展示文案:极客日志V2 zeeklog

更多推荐文章

查看全部
  • Telegram 关键词搜索机器人搭建指南(含 Python 脚本)
  • AI、机器学习与深度学习的本质区别及落地选型指南
  • Spring Boot 药品进销存信息管理系统设计与实现
  • Ubuntu 部署 OpenClaw 完整教程
  • Java 安全认证与权限控制实战
  • Win10/11 如何彻底关闭 Windows Defender 杀毒软件
  • SnapAny 视频解析下载工具:支持多平台与多种格式
  • Linux 信号保存与递达机制详解
  • WebSocket 实战:基于 Spring Boot 构建实时通信系统
  • OpenClaw 本地部署配置飞书机器人指南
  • SpringAI 实现连续对话:上下文记忆与会话隔离
  • VS Code Copilot 配置文件提示未知工具警告
  • 使用 OpenClaw 和飞书搭建多 Agent AI 助理团队
  • Ollama 模型下载慢?国内镜像 + LLama-Factory 微调方案
  • VSCode 与 PyCharm 配置 OpenCV 实战指南(Python 与 C++)
  • WinForm 集成 SqlSugar 与 SQLite 实战指南
  • OpenClaw 多机器人团队协作构建指南
  • Python 基础语法入门:常量、变量与运算符
  • 渗透测试人员必备工具:Kali Linux、Nmap、Metasploit 等 10 款核心软件详解
  • STL map/multimap 深度解析:接口用法与核心特性

相关免费在线工具

  • 加密/解密文本

    使用加密算法(如AES、TripleDES、Rabbit或RC4)加密和解密文本明文。 在线工具,加密/解密文本在线工具,online

  • Gemini 图片去水印

    基于开源反向 Alpha 混合算法去除 Gemini/Nano Banana 图片水印,支持批量处理与下载。 在线工具,Gemini 图片去水印在线工具,online

  • Base64 字符串编码/解码

    将字符串编码和解码为其 Base64 格式表示形式即可。 在线工具,Base64 字符串编码/解码在线工具,online

  • Base64 文件转换器

    将字符串、文件或图像转换为其 Base64 表示形式。 在线工具,Base64 文件转换器在线工具,online

  • Markdown转HTML

    将 Markdown(GFM)转为 HTML 片段,浏览器内 marked 解析;与 HTML转Markdown 互为补充。 在线工具,Markdown转HTML在线工具,online

  • HTML转Markdown

    将 HTML 片段转为 GitHub Flavored Markdown,支持标题、列表、链接、代码块与表格等;浏览器内处理,可链接预填。 在线工具,HTML转Markdown在线工具,online