(一)设计包含min函数的栈

    技术2022-05-20  44

    题目:定义栈的数据结构,要求添加一个min函数,能够得到栈的最小元素。要求函数min、push以及pop的时间复杂度都是O(1)。

     

    分析:普通的栈push(),pop()都是O(1),现在需要加入min方法。第一眼看这个题,想到在栈结构中加一个min变量,保存当前栈最小元素。这样在push()操作时比较当时元素与min变量值来决定是否要替换min变量,即push()操作O(1),但是pop()的时候最有麻烦,因为如果pop()的是最小元素,那更新min变量就需要重新遍历整个栈,时间复杂为O(n)。如果继续按上面思路想下去,再加一个次小变量仍然解决不了pop()时更新的问题。所以需要定义一个辅助栈存当前栈中的最小值,也就是需要一个是正常的数据栈,一个是存放最小元素的辅助栈。push的时候,如果辅助栈为空,则直接把当前元素压入辅助栈。否则比较当前元素值与辅助栈顶元素值(即之前最小值),取最小者压入栈。pop的时候与数据栈同时。最后提一个优化的地方,辅助栈可以不保存数据本身,而是只保存数据在数据栈的索引,这样可以减少内存使用。下面的实现使用STL的stack,没有办法用迭代器访问stack中间元素,所以辅助栈保存数据本身而并非索引。

     

    C++实现:

    #include <iostream> #include <stack> using namespace std; template <typename T> class minStack{ public: void push(const T&); void pop(); T& top(); T& min(); bool empty(){return s.empty();} int size(){return s.size();} private: stack<T> s; stack<T> minVal; }; template <typename T> void minStack<T>::push(const T& x){ s.push(x); if(minVal.size()==0){ minVal.push(x); }else if(minVal.top()>=x){ minVal.push(x); }else if(minVal.top()<x){ minVal.push(minVal.top()); } } template <typename T> void minStack<T>::pop(){ if(s.size()!=0){ s.pop(); minVal.pop(); }else{ cout << "Error: stack empty!!" << endl; } } template <typename T> T& minStack<T>::top(){ return s.top(); } template <typename T> T& minStack<T>::min(){ return minVal.top(); } template <typename T> void printStack(minStack<T> m){ if(!m.empty()){ cout << "min:" << m.min()<<"/t("<<m.top(); m.pop(); while(!m.empty()){ cout << ", " << m.top(); m.pop(); } cout << ")" << endl; }else{ cout << "stack empty" << endl; } } int main() { minStack<int> ms; ms.push(4); cout << "push 4!/t"; printStack(ms); ms.push(3); cout << "push 3!/t"; printStack(ms); ms.push(2); cout << "push 2!/t"; printStack(ms); ms.push(1); cout << "push 1!/t"; printStack(ms); ms.push(5); cout << "push 5!/t"; printStack(ms); while(!ms.empty()){ ms.pop(); cout << "pop!/t"; printStack(ms); } return 0; }


    最新回复(0)