我的解法:时间复杂度太高,不能提交;但思想我想是对的;
class Solution {
public:
int trap(vector<int>& height) {
//如何找到左侧最高:
//当前元素i找到左右两侧的尽头,只要两侧都有大于当前元素值的,记录下那个遍历到的最大的值;
// 当前元素的宽度(也就是1) * min(左侧最大值,右侧最大值) - 自身元素的高度;
//如果找到两侧尽头,只要有一侧小于自身元素值得,当前元素对应的结果就为0;
int result = 0;
for(int i = 0; i < height.size(); i++)
{
int flagl = -1;
int socl = height[i];
int flagr = -1;
int socr = height[i];
for(int left = i - 1;left >= 0; left--)
{
if(height[left] > socl)
{
flagl = left;
socl = height[left];
}
}
for(int right = i + 1; right< height.size();right++ )
{
if(height[right] > socr)
{
flagr = right;
socr = height[right];
}
}
if(flagl == -1 || flagr == -1)
{
result += 0;
}
else
{
result += min(height[flagl],height[flagr]) - height[i];
}
}
return result;
}
};
二分法:
class Solution {
public:
int trap(vector<int>& height) {
//双指针法:
// 用一个值来接受指针指向的值和当前最大值比较之后的最大值:每次都是相邻的两个比较;
//判断左指针和右指针谁高:
//右指针高则:左指针当前指向的坐标接的雨水 = 左侧最大值 - 当前值(这里的左侧最大值统计了当前值,若当前值是最大值,则不能接到雨水,相减也就为0);
//为什么左侧值小于右侧值的时候,计算左侧值?
// 对于某一个坐标来说,其能存储多少水,取决于那一侧低(也就是说此时计算左侧的,是因为左侧的已经被确定了;)
//假设,右侧的普遍偏低,左侧的高,那么左指针是不动的,也就是不会计算此时左指针指向的坐标的值,直到右指针找到一个高值,此时和left指向的值比较,发现左小于右,那么就按照左侧来计算;
//也就是说:左右指针都充当着往结果里添加值的遍历
int result = 0;
int left = 0, leftMax = 0;
int right = height.size() - 1, rightMax = 0;
while(left < right)
{
leftMax = max(leftMax, height[left]);
rightMax = max(rightMax, height[right]);
//其实最右侧是不是最大值,没关系,只要右边的值比左边的大,让左边的值称为决定性因素即可;例如,左侧最大值(包括当前值)是3,当前值是1,右侧存在10,8;
//甭管右侧最大值是先取到8,还是10,当前值存储的雨水的量是由左侧决定的;因为3只要小于右侧最大值即可;只要小于;
if(height[left] < height[right])
{
result += leftMax - height[left];
left++;
}
else
{
result += rightMax - height[right];
right--;
}
}
return result;
}
};