【503.下一个更大元素II】
这个题目不一样的地方在于,题目的条件是一个循环数组,循环数组的话可以使用如下的for循环来遍历。
for(int i = 0; i < nums.size() * 2; i++)
其中操作的时候使用 i % nums.size()
其他地方跟496.下一个更大元素 I的代码一样
class Solution {
public:
vector<int> nextGreaterElements(vector<int>& nums) {
vector<int> result(nums.size(), -1);
stack<int> st;
st.push(0);
for(int i = 1; i < nums.size() * 2; i++){
while(!st.empty() && nums[i%nums.size()] > nums[st.top()]){
result[st.top()] = nums[i%nums.size()];
st.pop();
}
st.push(i%nums.size());
}
return result;
}
};
【42. 接雨水】
这个题目有三种不同的方法去解题。
双指针法
动态规划法
单调栈法
双指针法和动规的方法是按照列的方式去收集雨水,分别找到每一个下标左边第一个比他大的元素和右边第一个比他大的元素,这样就可以计算出当前下标出能收集到的雨水的面积了。
但是单调栈不一样。单调栈是按照行的方式去收集雨水的。
遍历的逻辑是:
当遍历到的下标的元素小于栈顶的元素的时候,就将下标推入栈中。
当遍历到的下标的元素等于栈顶的元素的时候,就将栈顶的元素弹出,再把当前下标推入栈顶。
当遍历到的下标的元素大于栈顶的元素的时候,我们先将栈顶元素弹出,就可以计算此时这一层能搜集到的雨水的面积,最后将蛋钱下标推入栈顶。
class Solution {
public:
int trap(vector<int>& height) {
if(height.size() <= 2)return 0; //012长度的数组不可以接到雨水
stack<int> st; //单调栈
int sum = 0; //结果
st.push(0); //先把第一个下标给推入栈中
for(int i = 1; i < height.size(); i++){
if(height[i] < height[st.top()]){
st.push(i);
}else if(height[i] == height[st.top()]){
st.pop();
st.push(i);
}else{
while(!st.empty() && height[i] > height[st.top()]){ //非空才计算,空了不计算
int mid = st.top();
st.pop();
if(!st.empty()){
int h = min(height[st.top()], height[i]) - height[mid];
int w = i - st.top() - 1;
sum += h * w;
}
}
st.push(i);
}
}
return sum;
}
};