题型总结——栈的应用

1栈的原理

栈是一种线性表,仅在表尾进行插入和删除的线性表,称为栈顶。是按照先进后出的原则储存数据。

2栈的适用场景

  • 维持最值属性:在遍历线性表时需要需要维持遍历过程中的最大\最小值
  • 匹配后删除:入栈后等待匹配然后再退栈,实现局部动态匹配,达到全局的匹配
  • 二叉树的遍历
  • 图的深度优先算法

3例题分析

3.1有效的括号匹配

示例1:20.有效的括号
题目描述
给定一个只包括 ‘(’,’)’,’{’,’}’,’[’,’]’ 的字符串,判断字符串是否有效。

有效字符串需满足:

  • 左括号必须用相同类型的右括号闭合。
  • 左括号必须以正确的顺序闭合。

注意空字符串可被认为是有效字符串。

输入输出示例
示例 1:
输入: “()”
输出: true

示例 2:
输入: “()[]{}”
输出: true

示例 3:
输入: “(]”
输出: false

示例 4:
输入: “([)]”
输出: false

直观思想
先将括号对放置HashMap中,当遍历字符串时,当遇到左括号后我们期望在后续的遍历中能够遇到同类的右括号,所以先把左括号放入栈顶,当遍历到同类的括号时,出栈完成一次括号匹配。
代码实现

class Solution {
    private HashMap<Character, Character> mappings;

    public Solution(){
        this.mappings = new HashMap<Character, Character>();
        this.mappings.put(')', '(');
        this.mappings.put(']', '[');
        this.mappings.put('}', '{');
    }

    public boolean isValid(String s) {
        Stack<Character> stack = new Stack<>();
        for (int i = 0; i < s.length(); i++){
            char c = s.charAt(i);
            if (this.mappings.containsKey(c)){
                char topElement = stack.empty() ? '#' : stack.pop();
                char ch = this.mappings.get(c);
                if (topElement != ch){
                    return false;
                }
            }
            else{
                stack.push(c);
            }
        }
        return stack.isEmpty();
    }
}

3.2接雨水问题

示例2:42.接雨水
题目描述
给定 n 个非负整数表示每个宽度为 1 的柱子的高度图,计算按此排列的柱子,下雨之后能接多少雨水。
在这里插入图片描述
上面是由数组 [0,1,0,2,1,0,1,3,2,1,2,1] 表示的高度图,在这种情况下,可以接 6 个单位的雨水(蓝色部分表示雨水)。
输入输出描述
输入: [0,1,0,2,1,0,1,3,2,1,2,1]
输出: 6
直观思想
遍历数组时维护一个栈,如果当前的条形块小于或等于栈顶的条形块,我们将条形块的索引入栈,意思是当前的条形块被栈中的前一个条形块界定。如果我们发现一个条形块长于栈顶,我们可以确定栈顶的条形块被当前条形块和栈的前一个条形块界定,因此我们可以弹出栈顶元素并且累加答案到ans 。
算法流程:

  • 使用栈来储存数组的索引下标
  • 遍历数组:
    \quad 当栈非空且 height [ c u r r e n t ] > height [ s t . t o p ( ) ] \text{height}[current]>\text{height}[st.top()] height[current]>height[st.top()]
    \qquad 意味着栈中元素可以被弹出。弹出栈顶元素 t o p top top
    \qquad 计算当前元素和栈顶元素的距离,准备进行填充操作
    d i s t a n c e = c u r r e n t − s t . t o p ( ) − 1 \qquad distance=current−st.top()−1 distance=currentst.top()1
    b o u n d e d h e i g h t = m i n ( h e i g h t [ c u r r e n t ] , h e i g h t [ s t . t o p ( ) ] ) − h e i g h t [ t o p ] \qquad bounded_height=min(height[current],height[st.top()])−height[top] boundedheight=min(height[current],height[st.top()])height[top]找出界定高度
    \qquad 往结果中添加积水量, a n s + = d i s t a n c e × b o u n d e H e i g h t ans+=distance \times boundeHeight ans+=distance×boundeHeight

\qquad 将当前索引下标入栈
\qquad 将 c u r r e n t 将current current移动到下一个位置
代码实现

    public int trap(int[] height) {
        int ans = 0, current = 0;
        Stack<Integer> stack = new Stack<>();
        while (current < height.length) {
            while (!stack.isEmpty() && height[current] > height[stack.peek()]) {
                int top = stack.pop();
                if (stack.isEmpty()) break;
                int distance = current - stack.peek() - 1;
                int boundedHeight = Math.min(height[current], height[stack.peek()]) - height[top];
                ans += distance * boundedHeight;
            }
            stack.push(current++);
        }
        return ans;
    }

4栈的常用方法

  • E push(E item)将item压入栈顶
  • synchronized E peek()获得栈顶元素
  • synchronized E pop()移出栈顶对象,并且将该对象作为返回值
  • synchronized boolean isEmpty()判断该栈是否为空
  • boolean contains(Object o)该栈是否包含对象
  • synchronized E firstElement()返回栈底元素
  • synchronized E lastElement()返回栈顶元素

题型总结目录

题型总结——前K系列(堆、优先队列).
题型总结——二分查找(中间点计算的改进).
题型总结——二维数组(矩阵)之逆逆时针输出、查找.
题型总结——栈的应用.
题型总结——双指针算法全部模型(持续更新).

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值