Leetcode 11. Container With Most Water 盛最多水的容器 解法
題目如下:
Given n non-negative integers a1, a2, ..., an , where each represents a point at coordinate (i, ai). n vertical lines are drawn such that the two endpoints of line i is at (i, ai) and (i, 0). Find two lines, which together with x-axis forms a container, such that the container contains the most water.
Note: You may not slant the container and n is at least 2.
The above vertical lines are represented by array [1,8,6,2,5,4,8,3,7]. In this case, the max area of water (blue section) the container can contain is 49.
Example:
Input: [1,8,6,2,5,4,8,3,7] Output: 49
個人比較菜,第一反應DP,但發現這個DP沒什麼聯絡。。。。
解法1:
最直接的暴力匹配
時間複雜度:O(n^2)
空間複雜度:O(1)
解法2:
雙指標法
雙指標法的一個典型例題就是283. Move Zeroes
考慮該問題,結果矩形的大小為 (x2 - x1)* min(height(x1)height(x2));
那麼當x2-x1 增大時,即x1不變x2增大或x2不變,x1增小時,通俗的來說就是2個指標從中心向2邊擴散增加底部寬度,但這種方式需要確定起始的中心點在哪,而且會存在有一邊掃描不到的情況,此外,無法確定到底是向左還是向右擴散
那麼考慮從兩邊向中心聚攏,這種情況下有一種很確定的情況,那就是當向內縮小的方向的height值大時,總的面積大小肯定是減小的,因為高度取決於height中最小的那個,而底部寬度是在不斷減小的,那麼只需要每次將height值最小的方向向內縮小即可,並且此方法可保證掃描到所有情況
程式碼如下:
class Solution {
public:
int maxArea(vector<int>& height) {
int maxVal = 0;
int left = 0;
int right = height.size()-1;
while(left!=right)
{
int maxHeight = min(height[right],height[left]);
maxVal = max((right- left)*maxHeight,maxVal);
if(height[left]>height[right])
--right;
else
++left;
}
return maxVal;
}
};