zoukankan      html  css  js  c++  java
  • 【剑指offer】面试题21:包含min函数的栈

    题目:定义栈的数据结构,请在该类型中实现一个能够得到栈的最小元素的min函数。在该栈中,调用min、push及pop的时间复杂度都是O(1)。

    我们或许会想到在栈里添加一个成员变量存放最小的元素。

    具体思路为:每次压入一个新元素进栈的时候,如果该元素比当前最小的元素还要小,则更新最小元素。

    但是上述办法存在一个问题:如果我们做弹出操作,恰好弹出的是栈当前的最小元素?那么如何得到下一个最小的元素呢?

    为此,在push一个元素的时候,我们需要辅助栈保存之前的最小元素。

    具体做法为:每次push进一个元素val的时候,我们都将val与当前辅助栈的栈顶元素(最小元素)比较,然后将两者的较小者压入辅助栈,那么就能保证辅助栈的栈顶一直都是最小元素。当最小元素从数据站内被弹出之后,同时弹出辅助栈的栈顶元素,此时辅助栈的新栈顶元素就是下一个最小值。

    待压入序列为:3、4、2、1、0;具体操作、数据栈、辅助栈以及最小值如下表所示

     

    具体代码如下:

    StackWithMin.hpp

     1 // StackWithMin.hpp
     2 #ifndef STACKWITHMIN
     3 #define STACKWITHMIN 
     4 
     5 #include <stack>
     6 #include <assert.h>
     7 
     8 template <typename T> 
     9 class StackWithMin
    10 {
    11 public:
    12     StackWithMin() { }
    13     ~StackWithMin() { }
    14 
    15     const T& top()const;
    16 
    17     bool empty()const;
    18     size_t size()const;
    19 
    20     void push(const T &elem);
    21     void pop();
    22 
    23     const T& min()const; 
    24 
    25 private:
    26     std::stack<T> m_data; // 数据栈
    27     std::stack<T> m_tmp; // 辅助栈
    28 };
    29 
    30 template <typename T> 
    31 const T& StackWithMin<T>::top()const
    32 {
    33     return m_data.top();
    34 }
    35 
    36 template <typename T> 
    37 bool StackWithMin<T>::empty()const
    38 {
    39     return m_data.empty();
    40 }
    41 
    42 template <typename T> 
    43 size_t StackWithMin<T>::size()const
    44 {
    45     return m_data.size();
    46 }
    47 
    48 template <typename T> 
    49 void StackWithMin<T>::push(const T &elem)
    50 {
    51     // 放入数据栈
    52     m_data.push(elem);
    53 
    54     // 放入辅助栈
    55     // 如果比现有最小值小,则push该elem;如果比现有最小值大,则push辅助栈的栈顶
    56     if(m_tmp.empty() || m_tmp.top() > elem)
    57         m_tmp.push(elem);
    58     else
    59         m_tmp.push(m_tmp.top());
    60 }
    61 
    62 template <typename T> 
    63 void StackWithMin<T>::pop()
    64 {
    65     assert(!m_data.empty() || !m_tmp.empty());
    66 
    67     m_data.pop();
    68     m_tmp.pop();
    69 }
    70 
    71 template <typename T> 
    72 const T& StackWithMin<T>::min()const
    73 {
    74     return m_tmp.top();
    75 }
    76 
    77 #endif/* STACKWITHMIN */
    View Code

    测试代码如下:

    main.cpp

     1 // main.cpp
     2 #include "StackWithMin.hpp"
     3 #include <iostream>
     4 #include <time.h>
     5 #include <stdlib.h>
     6 using namespace std;
     7 
     8 int main(int argc, char const *argv[])
     9 {
    10     srand(time(NULL));
    11     StackWithMin<int> st;
    12 
    13     int n = 10;
    14 
    15     while(n--)
    16     {
    17         int num = rand() % 100;
    18         cout << "Push num " << num;
    19         st.push(num);
    20         cout << ", Test " << (10-n) << ": Min num is " << st.min() << endl;
    21     }
    22     cout << "The size is: " << st.size() << endl;
    23 
    24     while(++n < 5)
    25     {
    26         st.pop();
    27     }
    28     cout << "The min num is: " << st.min() << endl;
    29     cout << "The size is: " << st.size() << endl;
    30     
    31     return 0;
    32 }
    View Code

    本文完。

  • 相关阅读:
    1120. Maximum Average Subtree 子树平均值的最大值
    490. The Maze 迷宫踢足球
    323. Number of Connected Components in an Undirected Graph 连通图的数量
    done infosys_不告你答案的面试
    MyBatis(三)全局配置文件 之 typeHandlers 类型处理器
    MyBatis(三)全局配置文件 之 typeAliases 类型命名
    MyBatis(三)全局配置文件 之 properties 属性
    MyBatis(三)全局配置文件 之 settings 设置
    MyBatis(三)全局配置文件
    MyBatis(二)HelloWorld 案例
  • 原文地址:https://www.cnblogs.com/xfxu/p/4616496.html
Copyright © 2011-2022 走看看