题目:每日温度

使用到的是单调栈

首先想到的是双重循环遍历😅……..但这会导致n方的复杂度,所以这个方法不好

我们想要的是,通过一次遍历就可以找到所有符合条件的结果,这就意味着需要使用一种数据结构来存储遍历过的元素,再在之后的循环中进行比较

单调栈就是指,在入栈过程中,通过不断剔除不符合条件的元素,以保持栈内的元素按照某种单调性排列,即有序性,这与此题的要求高度吻合

所以在代码中,我们定义了一个stack,用于存储需要进行比较的数组的下标(至于为什么不存元素,这是因为后面我们需要用这个下标找到输出结果中对应的位置,并且距离计算使用的也是下标)

具体的运作原理是:栈顶元素是上一次循环留下来的结果,将栈顶元素与当前元素进行比较,如果当前元素更大,就认为栈顶元素找到了第一个更高温度,此时让栈顶元素出栈,因为他已经比较完毕了;由于while循环,若此时栈不为空,那么就会再次进行比较,如果当前元素更小,就入栈,这也就是选择单调栈的原因(保持了大小的有序性)

注意:这里可以进行优化,主要是把多次调用的函数提前保存,避免调用函数的开销(因为这是在循环中,所以开销会很大)

 1//
 2// 优化前(33ms)
 3//
 4vector<int> dailyTemperatures(vector<int>& temperatures)
 5{
 6    std::stack<int> st;
 7    st.push(0);
 8    int sz = temperatures.size();
 9    std::vector<int> res(sz, 0);
10
11    for(int j = 1; j < sz; j++)
12    {
13        while(!st.empty() && temperatures[st.top()] < temperatures[j])
14        {
15            res[st.top()] = j - st.top();
16            st.pop();
17        }
18        st.push(j);
19    }
20    return res;
21}
22
23//
24// 优化后(28ms)
25//
26vector<int> dailyTemperatures(vector<int>& temperatures)
27{
28    std::stack<int> st;
29    int sz = temperatures.size();
30    std::vector<int> res(sz, 0);
31
32    for(int j = 0; j < sz; j++)
33    {
34        int t = temperatures[j];
35        while(!st.empty() && temperatures[st.top()] < t)
36        {
37            int k = st.top();
38            res[k] = j - k;
39            st.pop();
40        }
41        st.push(j);
42    }
43    return res;
44}