您的位置:首页 > 职场人生

面试题精选(80):设计含min函数的栈的另解

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

 

分析:

 

下面给出的链接是之前使用双倍空间2*n来实现的

http://blog.csdn.net/yysdsyl/archive/2007/10/24/1841644.aspx

 

其实,辅助栈的使用可以进一步优化,做到worst-case下使用n空间,从而更大程度上节省空间:

 

template <typename T> class MinStack {
    stack<T> _stack, _min;

public:
    MinStack() { }

    void push(const T & x) {
        _stack.push(x);
        if (_min.empty() || !(x < _min.top())) _min.push(x);
    }

    T pop() {
        T x = _stack.top();
        _stack.pop();
        if (x == _min.top()) _min.pop();
        return T;
    }

    T getMin() {
        return _min.top();
    }
};

 

 

 

不过即使在辅助栈的使用上作了必要的优化,但是空间的使用在worst-case下依旧是个问题,那么有没有更好的解决办法呢?下面将给出一个O(n+1)空间复杂度的设计方法:(用diff来压缩)

void push(int elem) {
    if (stack.empty()) {
        stack.push(elem);
        stack.push(elem);
    } else {
        int min = stack.pop();
        stack.push(elem - min);
        stack.push(elem < min ? elem: min);
    }
}

 

int pop() {
    int min = stack.pop(), elem = stack.pop();
    if (elem < 0) {
        stack.push(min - elem);
        return min;
    } else {
        if (!stack.empty()) stack.push(min);
        return elem + min;
    }
}

 

int min() const {
    int min = stack.pop();
    stack.push(min);
    return min;
}

 

过程模拟:

clear(): [ ]
push(3): [3 3]
push(4): [3 1 3]
push(2): [3 1 -1 2]
push(5): [3 1 -1 3 2]
push(1): [3 1 -1 3 -1 1]
push(1): [3 1 -1 3 -1 0 1]
push(6): [3 1 -1 3 -1 0 5 1]
push(7): [3 1 -1 3 -1 0 5 6 1]

min() --> 1; pop() --> 7: [3 1 -1 3 -1 0 5 1]
min() --> 1; pop() --> 6: [3 1 -1 3 -1 0 1]
min() --> 1; pop() --> 1: [3 1 -1 3 -1 1]
min() --> 1; pop() --> 1: [3 1 -1 3 2]
min() --> 2; pop() --> 5: [3 1 -1 2]
min() --> 2; pop() --> 2: [3 1 3]
min() --> 3; pop() --> 4: [3 3]
min() --> 4; pop() --> 3: [ ]

 

 

 

 
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息