class Solution {
public int trap(int[] height) {
if (height == null || height.length == 0) {
return 0;
}
int n = height.length;
int totalWater = 0;
java.util.Stack<Integer> stack = new java.util.Stack<>();
for (int i = 0; i < n; i++) {
while (!stack.isEmpty() && height[i] > height[stack.peek()]) {
int top = stack.pop(); // 当前柱子的索引
if (stack.isEmpty()) {
break; // 栈为空时无法形成凹槽
}
int left = stack.peek(); // 左边界的索引
int width = i - left - 1; // 两柱子之间的宽度
int boundedHeight = Math.min(height[i], height[left]) - height[top]; // 有效的高度
totalWater += width * boundedHeight; // 计算当前凹槽可以存的水量
}
stack.push(i); // 将当前柱子的索引入栈
}
return totalWater;
}
}
class Solution {
public int trap(int[] height) {
Stack<Integer> stack = new Stack<Integer>();
stack.push(0);
int sum = 0;
for(int i = 1; i < height.length; i ++){
int current = height[i];
int popNum = stack.peek();
if(current <= height[popNum]){
stack.push(i);
}else if(current > height[popNum]){
// 当前遇到 一个更高的 计算 体积
while(!stack.isEmpty() && current > height[popNum]){
popNum = stack.pop();
if(stack.isEmpty()){
break;
}
int left = stack.peek();
int waterWidth = i - left - 1;
int waterHeight = Math.min(height[left], current) - height[popNum];
sum += (waterHeight * waterWidth);
popNum = stack.peek();
}
stack.push(i);
}
}
return sum;
}
}
共以下 5 个回答
解题思路
– 定义2个dp: int[] leftdp 在i时左边的最大值; int[] rightdp 在i时右边的最大值
– 在i点,取 leftdp[i]、rightdp[i]的最小值最为容器的高
– 容量=宽(1)*高,其中高=容器的高-height[i]
【题解1】
单调栈解法O(n)
使用两个数组分别记录左边最高的柱子与右边最高的柱子,雨水量为柱子高度的最小值减去高度。
时间复杂度O(N),空间复杂度O(N)。
//双指针解法
class Solution {
public int trap(int[] height) {
if (height null || height.length 0) {
return 0;
}
}
思路: 使用单调栈处理