• LeetCode155:最小栈


    设计一个支持 push ,pop ,top 操作,并能在常数时间内检索到最小元素的栈。
    实现 MinStack 类:
    MinStack() 初始化堆栈对象。
    void push(int val) 将元素val推入堆栈。
    void pop() 删除堆栈顶部的元素。
    int top() 获取堆栈顶部的元素。
    int getMin() 获取堆栈中的最小元素。
    在这里插入图片描述

    解法一

    这道题最直接的解法就是我们可以用两个栈,一个栈去保存正常的入栈出栈的值,另一个栈去存最小值,也就是用栈顶保存当前所有元素的最小值。存最小值的栈的具体操作流程如下:
    将第一个元素入栈。
    新加入的元素如果大于栈顶元素,那么新加入的元素就不处理。
    新加入的元素如果小于等于栈顶元素,那么就将新元素入栈。
    出栈元素不等于栈顶元素,不操作。
    出栈元素等于栈顶元素,那么就将栈顶元素出栈。

    入栈 3 
    |   |    |   |
    |   |    |   |
    |_3_|    |_3_|
    stack  minStack
    
    入栈 5 , 5 大于 minStack 栈顶,不处理
    |   |    |   |
    | 5 |    |   |
    |_3_|    |_3_|
    stack  minStack
    
    入栈 2 ,此时右边的 minStack 栈顶就保存了当前最小值 2 
    | 2 |    |   |
    | 5 |    | 2 |
    |_3_|    |_3_|
    stack  minStack
    
    出栈 2,此时右边的 minStack 栈顶就保存了当前最小值 3
    |   |    |   |
    | 5 |    |   |
    |_3_|    |_3_|
    stack  minStack
    
    出栈 5,右边 minStack 不处理
    |   |    |   |
    |   |    |   |
    |_3_|    |_3_|
    stack  minStack
    
    出栈 3
    |   |    |   |
    |   |    |   |
    |_ _|    |_ _|
    stack  minStack
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35

    代码

    class MinStack {
        private Stack<Integer> stack;
        private Stack<Integer> minStack;
    
        public MinStack() {
            stack = new Stack<>();
            minStack = new Stack<>();
        }
    
        public void push(int val) {
            stack.push(val);
            if (!minStack.isEmpty()) {
                int top = minStack.peek();
                if (val <= top) {
                    minStack.push(val);
                }
            } else {
                //辅助栈没有值的时候,直接push
                minStack.push(val);
            }
        }
    
        public void pop() {
            int pop = stack.pop();
            int top = minStack.peek();
            //如果栈与辅助栈的最上边的数字一样在出栈
            if (pop == top) {
                minStack.pop();
            }
        }
    
        public int top() {
            return stack.peek();
        }
    
        public int getMin() {
            return minStack.peek();
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39

    解法二

    如果只用一个变量就会遇到一个问题,如果把 min 更新为 2,那么之前的最小值 3 就丢失了。
    怎么把 3 保存起来呢?把它在 2 之前压入栈中即可。

    入栈 2 ,同时将之前的 min 值 3 入栈,再把 2 入栈,同时更新 min = 2
    | 2 |   min = 2
    | 3 |  
    | 5 |     
    |_3_|    
    stack  
    
    入栈 6 
    | 6 |  min = 2
    | 2 |   
    | 3 |  
    | 5 |     
    |_3_|    
    stack  
    
    出栈 6     
    | 2 |   min = 2
    | 3 |  
    | 5 |     
    |_3_|    
    stack  
    
    出栈 2     
    | 2 |   min = 2
    | 3 |  
    | 5 |     
    |_3_|    
    stack  
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28

    上边的最后一个状态,当出栈元素是最小元素我们该如何处理呢?
    我们只需要把 2 出栈,然后再出栈一次,把 3 赋值给 min 即可。

    出栈 2     
    |   |  min = 3   
    | 5 |   
    |_3_|    
    stack  
    
    • 1
    • 2
    • 3
    • 4
    • 5

    当有更小的值来的时候,我们只需要把之前的最小值入栈,当前更小的值再入栈即可。当这个最小值要出栈的时候,下一个值便是之前的最小值了。
    代码

    class MinStack {
        int min = Integer.MAX_VALUE;
        Stack<Integer> stack = new Stack<Integer>();
        public void push(int x) {
            //当前值更小
            if(x <= min){   
                //将之前的最小值保存
                stack.push(min);
                //更新最小值
                min=x;
            }
            stack.push(x);
        }
    
        public void pop() {
            //如果弹出的值是最小值,那么将下一个元素更新为最小值
            if(stack.pop() == min) {
                min=stack.pop();
            }
        }
    
        public int top() {
            return stack.peek();
        }
    
        public int getMin() {
            return min;
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
  • 相关阅读:
    无重复字符的最长子串 Golang leecode_3
    JUC笔记(四) --- 内存共享模型
    YOLO目标检测——红外人员数据集【含对应voc、coco和yolo三种格式标签+划分脚本】
    微软开源 MS-DOS「GitHub 热点速览」
    Shopee虾皮API接口:解锁商品买家评论数据的宝藏
    我的vue的学习之旅
    IT人的2022演讲
    坚信人类记忆是以大分子物质存储的朋友们请看过来
    【Router】PC连接到路由LAN,但是无法获取到IP地址问题分析及解决方案
    OPC UA:工业领域的“HTML”
  • 原文地址:https://blog.csdn.net/weixin_46426906/article/details/126775796