【 leetcode Top 100】11. 盛最多水的容器

题目:

在这里插入图片描述
这道题,说实话,打死我,我也想不到双指针做法,我只是觉得双for,肯定会超时,肯定有简单做法,但是万万没想到啊,还有这种操作。

代码:

class Solution {
public:
    int maxArea(vector<int>& height) {
        int i=0;int j=height.size()-1;
        int maxA = 0;
        while(i<j){
            maxA=max(maxA,(j-i)*min(height[i],height[j]));
            if(height[i]<=height[j])i++;
            else j--;
        }
        return maxA;
    }
};

证明:

这里的做法是双指针的做法,分别用一个指针来标识对应的容器的左右边界。

初始情况为
在这里插入图片描述
接下来就是怎么移动指针的问题,答案是移动较小的指针,证明如下:

假设对任意的容器的左右边界分别设为X和Y,设其中较小的为X,那么对应的容器的面积就为:

Area = min(X,Y) * t

故,此时如果移动较大的Y,的话,设下一次的Y为Y2,此时Y2或大于Y,或小于Y。

  • 若Y2>Y,则此时的min(X,Y2)仍然受X限制,即min(X,Y2) = X = min(X,Y),但此时 t 缩小了1,故Area无论如何都会变小
  • 若Y2<Y,此时的min(X,Y2)的结果或为X,或为Y2,即min(X,Y2) <= min(X,Y),并且,此时 t 缩小了1,故Area无论如何都会变小

如果移动较小的X,的话,设下一次的X为X2,此时X2或大于X,或小于X。

  • 若X2>X,则此时的min(X2,Y),就变得不可控了,或为X2,或为Y,
  • 若X2<X,则此时的min(X2,Y),就变为X2,即min(X2,Y) < X = min(X,Y),并且 t 缩小了1,故Area,无论如何都会缩小。

如上,只有一种可能,就是移动较小的X,这样才会有一丝机会使得Area变大。故每次移动都移动较小的指针。

此时,会有一个疑问,如果将X移除,那么以后会不会还会用到X,但X已经被我们遗弃了的情况:

分析如下:

我们将X移除,是因为X是较小的一方,以后如果遇到了需要用到X,无非是我们认为X可能和其他边界形成一个更大的Area,但是这是不可能的,
在这里插入图片描述

如,此时已经i,j到如此情况,X已经被淘汰,现在假设我们(X,Y)会形成了一个更大的图形,想像一下这种情况下可行吗?

现在存在两对(X,Y)(X,X被淘汰时的右边界),这两部分来说,(X,Y)的面积必然小于(X,X被淘汰时的右边界),也就是(X,Y)这种情况无意义,也就是当X被淘汰的同时,它和右边界内形成的所有面积对都将失效,都会小于(X,X被淘汰时的右边界)的面积。


如果(Y,X)形成了一个更大的面积,想一下这种情况下可行吗?

当Y被淘汰的时候,(Y,X)这个面积对,已经随着Y,被淘汰,变得失效了。

也就是如果X,还要用,那么都可以和X被淘汰的那个状态对比,结果都是必然小于当时那个状态的Area。
在这里插入图片描述
综上,这种方法巧妙,就巧妙在,他是每一次淘汰就淘汰一批配对,如:一开始Y被淘汰,那么对应的Y和右面的直到index(3)的所有配对都会被淘汰,此时移动到X处,开始淘汰index(6)到index(7)的所有配对,,这是就体现出来了为啥之前的Y,不再使用,再淘汰Y的时候,保留了(1,7)的对,淘汰7的时候,保留了(8,7),淘汰了6和7之间的所有的对,也就是(1,7)这个对,都已经不在考虑范围了,包括此时淘汰了(3,7),那么接下来淘汰3的时候,淘汰的是6到3之间的数,而(3,7)之前已经被淘汰过了。

也就是上面的思想还是,类似于枚举那种,来枚举取最大值,但是就是巧妙在淘汰一批配对上。而且这个枚举还是每个对,出现且只出现一次那种。

此时,上面的那个疑问,一个X,被淘汰后,后期还能不能再用的问题就迎刃而解了,因为这个也是枚举的思想,也就是对应于X的所有配对,其实之前都已经被考虑过了,在淘汰它的那一刻,它的所有枚举配对都已经被考虑完毕了,所以X就再无用处了。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值