单调栈解法
int trap(vector<int>& height) {
stack<int> stk;
int res=0;
for(int i=0;i<height.size();i++){
while(!stk.empty()&&height[i]>height[stk.top()]){
int mid = stk.top();
stk.pop();
if(!stk.empty()){
int l = stk.top();
int r = i;
res += (min(height[l],height[r])-height[mid])*(r-l-1);
}
}
stk.push(i);
}
return res;
}
动态规划解法
int trap(vector<int>& height) {
int dp[height.size()][2];
int n=height.size();
int result=0;
dp[0][0]=height[0];
dp[n-1][1]=height[n-1];
for(int i=1;i<n-1;i++){
dp[i][0]=max(height[i],dp[i-1][0]);
dp[n-i-1][1]=max(height[n-i-1],dp[n-i][1]);
}
for(int i=1;i<n-1;i++){
result+=min(dp[i][0],dp[i][1])-height[i];
}
return result;
}
双指针解法(优化动态规划)
int trap(vector<int>& height) {
//双指针解法
int n=height.size();
int left=0,right=n-1;
int l_max=height[0],r_max=height[n-1];
//l_max代表num[0...left]最大的元素,r_max代表num[right...n-1]最大的元素
//主要思路为:当l_max小于此时的r_max时,该元素右边真正的最大值就不会影响结果了,结果只由l_max决定。右边同理。
int res=0;
while(left<=right){
l_max=max(l_max,height[left]);
r_max=max(r_max,height[right]);
if(l_max<r_max){
res += l_max-height[left];
left++;
}else{
res += r_max-height[right];
right--;
}
}
return res;
}