42.接雨水
给定 n 个非负整数表示每个宽度为 1 的柱子的高度图,计算按此排列的柱子,下雨之后能接多少雨水。
上面是由数组 [0,1,0,2,1,0,1,3,2,1,2,1] 表示的高度图,在这种情况下,可以接 6 个单位的雨水(蓝色部分表示雨水)。
示例:
输入: [0,1,0,2,1,0,1,3,2,1,2,1]
输出: 6
思路:
1.单调栈:等到下一个数大于前一个数(栈顶的数),弹出当前的栈顶(凹槽),通过当前节点,当前栈顶元素,弹出的元素这三者来分别计算长和宽,计算面积;
2.注意栈是空的情况:左边或者右边没有数,也盛不了水;
考虑[1,0,0,1]的入栈过程,有助于理解while语句;
class Solution {
public int trap(int[] height) {
int n = height.length;
Stack<Integer> stack = new Stack<>();
int res = 0;
for (int index = 0; index < n; index++) {
while (!stack.isEmpty() && height[index] > height[stack.peek()]) {
int top = stack.pop();
if(stack.isEmpty())
break;
int h = Math.min(height[stack.peek()], height[index])-height[top];
int disc = index - stack.peek() - 1;
res += h * disc;
}
stack.push(index);
}
return res;
}
}