• 剑指 Offer 30. 包含min函数的栈 && Leetcode 155. 最小栈


    地址  https://leetcode-cn.com/problems/bao-han-minhan-shu-de-zhan-lcof/

    定义栈的数据结构,请在该类型中实现一个能够得到栈的最小元素的 min 函数在该栈中,调用 min、push 及 pop 的时间复杂度都是 O(1)。
    
     
    
    示例:
    
    MinStack minStack = new MinStack();
    minStack.push(-2);
    minStack.push(0);
    minStack.push(-3);
    minStack.min();   --> 返回 -3.
    minStack.pop();
    minStack.top();      --> 返回 0.
    minStack.min();   --> 返回 -2.
     
    
    提示:
    
    各函数的调用总次数不超过 20000 次
     
    
    注意:本题与主站 155 题相同:https://leetcode-cn.com/problems/min-stack/
    
     

    解答

    栈的操作基本没有变化 ,关键在于如何获取当前序列中最小的数。

    最开始考虑使用最小堆,但是最小堆的弹出的时间复杂度达不到题目要求

    我们从减少最小堆的不必要的存储和弹出的操作入手。如果当前push 的数据比最小堆的顶端最小数目大的话那么就不必push进入堆,

    因为该数字push进容器内,它在容器内的存活周期中他的下面始终有一个存活周期比它长比他小的数字,所以它的push和pop是没有必要的

    于是就可以大量减少最小堆的操作。

    代码如下

    class MinStack {
    public:
        /** initialize your data structure here. */
        stack<int>data;
        priority_queue<int, vector<int>, greater<int>> minHeap;
        MinStack() {
        }
    
        void push(int x) {
            data.push(x);
            if (minHeap.empty() || x <= minHeap.top() ) minHeap.push(x);
        }
    
        void pop() {
            if (data.empty()) return;
            int x = data.top(); data.pop();
            if (x <= minHeap.top()) minHeap.pop();
        }
    
        int top() {
            return data.top();
        }
    
        int min() {
            if (!minHeap.empty())
                return minHeap.top();
    
            return -999999;
        }
    };

    进一步的优化,观察以上的堆的操作

    堆的操作已经演变成一个只记录当前最小数字的单调栈了

    那么直接使用两个栈就可以完成以上操作

    ========================================================================================

    class MinStack {
    public:
        /** initialize your data structure here. */
        stack<int>data;
        stack<int>currMin;
        MinStack() {
        }
    
        void push(int x) {
            data.push(x);
            if (currMin.empty() || x <= currMin.top() ) currMin.push(x);
        }
    
        void pop() {
            if (data.empty()) return;
            int x = data.top(); data.pop();
            if (x <= currMin.top()) currMin.pop();
        }
    
        int top() {
            return data.top();
        }
    
        int min() {
            if (!currMin.empty())
                return currMin.top();
    
            return -999999;
        }
    };
    作 者: itdef
    欢迎转帖 请保持文本完整并注明出处
    技术博客 http://www.cnblogs.com/itdef/
    B站算法视频题解
    https://space.bilibili.com/18508846
    qq 151435887
    gitee https://gitee.com/def/
    欢迎c c++ 算法爱好者 windows驱动爱好者 服务器程序员沟通交流
    如果觉得不错,欢迎点赞,你的鼓励就是我的动力
    阿里打赏 微信打赏
  • 相关阅读:
    Mobile GMaps - Google Map移动版
    365Key今天不能用了,感觉不爽
    推荐:对个人免费的杀毒软件[avast!]
    向 Visual Studio 2005 Tools for Office 迁移时,将 VBA 代码转换为 Visual Basic .NET
    令人向往的3000年生活(转载)
    也说技术人员创业
    痛恨3721的朋友们,装个avast! Antivirus吧
    很Cool很全的Google Map的应用
    关于.net的企业应用开发
    天天网摘(20050704)
  • 原文地址:https://www.cnblogs.com/itdef/p/14403498.html
Copyright © 2020-2023  润新知