Given n non-negative integers representing an elevation map where the width of each bar is 1, compute how much water it is able to trap after raining.
The above elevation map is represented by array [0,1,0,2,1,0,1,3,2,1,2,1]. In this case, 6 units of rain water (blue section) are being trapped. Thanks Marcos for contributing this image!
Example:
Input: [0,1,0,2,1,0,1,3,2,1,2,1] Output: 6
分析
这道题很容易把问题想复杂了,我一共做了两遍,第一遍的做法是先找到中间最高的峰,然后再找到左边最高的和右边最高的山峰,分别记录左边和右边的,然后在找左边的左边和右边的右边。代码写起来很复杂,但是最终时间复杂度也是能满足要求的。
看到别人有一个很简单的算法,我们最重要的是要知道一个Index左边和右边最高的峰,如果min(maxRight, maxLeft) > height[index],那么这个点就会灌水,一直增长到min(maxRight, maxLeft)的高度。那么问题就变成我们分别计算一个点左边最高的和右边最高的峰。只需要利用两个数组记录就可以了。
Code
class Solution {
public:
int trap(vector<int>& height) {
int res = 0;
int length = height.size();
vector<int> maxLeft(length, 0);
vector<int> maxRight(length, 0);
int left = 0;
for (int i = 0; i < length; i++)
{
if (height[i] > left)
left = height[i];
maxLeft[i] = left;
}
int right = 0;
for (int i = length-1; i >= 0; i --)
{
if (height[i] > right)
right = height[i];
maxRight[i] = right;
}
for (int i = 1; i < length-1; i ++)
{
int minHeight = min(maxLeft[i-1], maxRight[i+1]);
if (minHeight > height[i])
res += minHeight - height[i];
}
return res;
}
};
运行效率
Runtime: 8 ms, faster than 98.95% of C++ online submissions for Trapping Rain Water.
Memory Usage: 9.1 MB, less than 99.63% of C++ online submissions forTrapping Rain Water.