题目:
给定 n 个非负整数表示每个宽度为 1 的柱子的高度图,计算按此排列的柱子,下雨之后能接多少雨水。
示例 1:
编辑
- 输入:height = [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 个单位的雨水(蓝色部分表示雨水)。
示例 2:
- 输入:height = [4,2,0,3,2,5]
- 输出:9
java:
public class Leetcode042 {
public static int trap(int[] height) {
int sum = 0;
for (int i = 0; i < height.length; i++) {
if (i == 0 || i == height.length - 1) {
continue;
}
//左高度.
int left = height[i];
//右高度.
int right = height[i];
for (int r = i + 1; r < height.length; r++) {
if (height[r] > right) {
right = height[r];
}
}
for (int l = i - 1; l >= 0; l--) {
if (height[l] > left) {
left = height[l];
}
}
int h = Math.min(left, right) - height[i];
if (h > 0) {
sum += h;
}
}
return sum;
}
//单调栈
public static int trap2(int[] height) {
int size = height.length;
if (size <= 2) {
return 0;
}
Stack<Integer> stack = new Stack<>();
stack.push(0);
int sum = 0;
for (int index = 1; index < size; index++) {
Integer stackTop = stack.peek();
if (height[index] < height[stackTop]) {
stack.push(index);
} else if (height[index] == height[stackTop]) {
//相等的左边无法存水.
stack.pop();
stack.push(index);
} else {
int heightAtIdx = height[index];
while (!stack.isEmpty() && (heightAtIdx > height[stackTop])) {
Integer mid = stack.pop();
if (!stack.isEmpty()) {
Integer left = stack.peek();
int h = Math.min(height[left], height[index]) - height[mid];
int w = index - left - 1;
int hold = h * w;
if (hold > 0){
sum += hold;
}
stackTop = stack.peek();
}
}
stack.push(index);
}
}
return sum;
}
public static void main(String[] args) {
int[] height1 = {0, 1, 0, 2, 1, 0, 1, 3, 2, 1, 2, 1};
int[] height2 = {0, 1, 0, 2, 1, 0, 1, 3, 2, 1, 2, 1};
System.out.println(trap2(height1));
System.out.println(trap(height2));
}
}
Go:
` package LeetCode
func Trap(nums []int) int { var left, right, leftMax, rightMax, result int right = len(nums) - 1 for left < right { if nums[left] < nums[right] { if nums[left] >= leftMax { leftMax = nums[left] } else { result += leftMax - nums[left] } left++ } else { if nums[right] > rightMax { rightMax = nums[right] } else { result += rightMax - nums[right] } right-- } } return result }
func Trap2(nums []int) int { if len(nums) <= 2 { return 0 } st := make([]int, 1, len(nums)) var res int for i := 1; i < len(nums); i++ { if nums[i] < nums[st[len(st)-1]] { st = append(st, i) } else if nums[i] == nums[st[len(st)-1]] { st = st[:len(st)-1] st = append(st, i) } else { for len(st) != 0 && nums[i] > nums[st[len(st)-1]] { top := st[len(st)-1] st = st[:len(st)-1] if len(st) != 0 { tmp := (min(nums[i], nums[st[len(st)-1]]) - nums[top]) * (i - st[len(st)-1] - 1) res += tmp } } st = append(st, i) } } return res }
func main() { array := []int{0, 1, 0, 2, 1, 0, 1, 3, 2, 1, 2, 1} trap := LeetCode.Trap(array) trap2 := LeetCode.Trap2(array) fmt.Println(trap) fmt.Println(trap2) }`
黯淡无光.
如果大家喜欢我的分享的话.可以关注我的微信公众号
念何架构之路