炎炎夏日,还是呆在空调房里切切题吧。

Container With Most Water,题意其实有点噱头,简化下就是,给一个数组,恩,就叫 height 吧,从中任选两项 i 和 j(i <= j),使得 Math.min(height[i], height[j]) * (j - i) 最大化,求解这个最大值。

O(n^2)

O(n^2) 复杂度的解法非常容易想到,直接两两枚举。

var maxArea = function(height) {
  var len = height.length;
  var maxn = 0;

  for (var i = 0; i < len; i++)
    for (var j = i + 1; j < len; j++)
      maxn = Math.max(maxn, Math.min(height[i], height[j]) * (j - i));

  return maxn;
};

提交,TLE,看了下数据,数组长度 1w,复杂度直接飙到亿级,不 TLE 才怪了。

O(nlogn)

我们假设数组为 [a1, a2, ..., an],我们实际需要求得的其实是一个子数组。假设这个子数组的最后一个元素是 a5,同时我们规定该子数组最后一个元素不大于第一个元素,那么实际我们需要求的是 a1, a2, a3, a4 中哪个元素比 a5 大(或者相同),并且这个元素越前面越好。

这样,我们可以遍历每个元素,将这个元素确定为子数组的最后一个元素,同时去求前面已经被遍历过的元素中,大于等于该元素并且最左的元素。对于求这个最左元素,我们可以维护一个单调递增的数组,用二分去解。

二分需要求解一个递增序列中,刚好大于等于指定元素的位置,这个 case 没有出现在 二分查找大集合(妈妈再也不用担心我的二分查找了),我们可以稍微变个形。

// 求解 a 数组中刚好大于等于 target 的位置
// 如果都小于 target 则返回 a.length
function binarySearch(a, target) {
  target += 1;
  var start = 0
    , end = a.length - 1;

  while(start <= end) {
    var mid = ~~((start + end) >> 1);
    if (a[mid] >= target)
      end = mid - 1;
    else
      start = mid + 1;
  }

  if (a[start - 1] === target - 1)
    start -= 1;
  return start;
}

还需要注意的一点是,必须正反来两次,因为我们假设子数组的最后一个元素小于等于首元素,还需要考虑另一种情况,即子数组首元素小于等于最后一个元素。

其他部分问题不大,具体代码可以参考 https://github.com/hanzichi/leetcode/blob/master/Algorithms/Container%20With%20Most%20Water/O(nlogn).js

提交,AC,击败 4% ... 势必还有更优的解法,而且根据我的经验,如果这是标程正解的话,这道题的难度应该是 Hard 而不是 Medium 了。

O(n)

正解的复杂度应该是 O(n) 的。

我们可以举个简单的例子,假设数组是 [2, 3, 4, 5, 4, 3],那么最长的子数组一定只有一个,即取全部元素,这样能装的水的数量是 2 * 5 。接下去我们的子元素,长度一定是会变小的,有两种情况,为 [2, 3, 4, 5, 4][3, 4, 5, 4, 3]。我们来看 [2, 3, 4, 5, 4],这种情况下,显然比取全部元素求得的结果 10 要小,为什么这么说?因为两者的基准都是按 2 来算的,但是取全部元素长度大。

似乎有点眉目了,再来看 [2, 3, 4, 5, 4, 3] 这个原始的数组,从中找出一个子数组,如果以 2 为子数组最左的元素,那么这个子数组求解的值(即装水的量),不可能比 [2, 3, 4, 5, 4, 3] 这个原始数组求到的 10 要大了,有木有?!因为该子数组装水的基准,是不可能比 2 大了的。

这样,我们似乎可以用一点点贪心去解这道题,一步步缩小子数组的大小。

while (start <= end) {
  maxn = Math.max(maxn, Math.min(height[end], height[start]) * (end - start));

  if (height[end] < height[start])
    end --;
  else
    start ++;
}

完整代码可以参考 https://github.com/hanzichi/leetcode/blob/master/Algorithms/Container%20With%20Most%20Water/O(n).js

如何装最多的水? — leetcode 11. Container With Most Water的更多相关文章

  1. [LeetCode] 11. Container With Most Water My Submissions Question 解题思路

    Given n non-negative integers a1, a2, ..., an, where each represents a point at coordinate (i, ai).  ...

  2. leetcode 11. Container With Most Water 、42. Trapping Rain Water 、238. Product of Array Except Self 、407. Trapping Rain Water II

    11. Container With Most Water https://www.cnblogs.com/grandyang/p/4455109.html 用双指针向中间滑动,较小的高度就作为当前情 ...

  3. Leetcode 11. Container With Most Water(逼近法)

    11. Container With Most Water Medium Given n non-negative integers a1, a2, ..., an , where each repr ...

  4. [LeetCode] 11. Container With Most Water 装最多水的容器

    Given n non-negative integers a1, a2, ..., an , where each represents a point at coordinate (i, ai). ...

  5. 蜗牛慢慢爬 LeetCode 11. Container With Most Water [Difficulty: Medium]

    题目 Given n non-negative integers a1, a2, ..., an, where each represents a point at coordinate (i, ai ...

  6. LeetCode 11. [👁] Container With Most Water & two pointers

    盛最多水的容器 给定 n 个非负整数 a1,a2,...,an,每个数代表坐标中的一个点 (i, ai) .在坐标内画 n 条垂直线,垂直线 i 的两个端点分别为 (i, ai) 和 (i, 0).找 ...

  7. LeetCode 11. Container With Most Water (装最多水的容器)

    Given n non-negative integers a1, a2, ..., an, where each represents a point at coordinate (i, ai).  ...

  8. [leetcode]11. Container With Most Water存水最多的容器

    Given n non-negative integers a1, a2, ..., an , where each represents a point at coordinate (i, ai). ...

  9. [LeetCode]11. Container With Most Water 盛最多水的容器

    Given n non-negative integers a1, a2, ..., an , where each represents a point at coordinate (i, ai). ...

随机推荐

  1. 如何在SSM项目配置springMVC校验框架validator

    1.在springMVC配置文件配置添加如下信息 <!-- 表单验证框架 --> <bean id="validator" class="org.spr ...

  2. 列表组件抽象(2)-listViewBase说明

    这是我写的关于列表组件的第2篇博客.前面的相关文章有: 1. 列表组件抽象(1)-概述 listViewBase是列表组件所有文件中最核心的一个,它抽象了所有列表的公共逻辑,将来如果有必要添加其它公共 ...

  3. 高分辨率下IE浏览器缩放导致出现右侧滚动条问题的解决

    0 问题描述 由于需要演示触控操作,采购了SurfacePro,SurfacePro的推荐分辨率为2736×1824,且默认缩放比例为200%,IE浏览器的默认缩放比例也是200%,这样就导致右侧出现 ...

  4. 基于NodeJS的秘室聊天室

    借着放假期间将NodeJS重新回顾了一下并玩了一下sketch来进行设计界面,很不错.(注:代码整理后会放到github上,请关注.) 本次聊天室我给它定义了一个名称叫“秘密聊天室”. 需求: 技术选 ...

  5. C# 高效编程笔记2

    C# 高效编程笔记2 1.理解GetHashCode()的陷阱 (1)作用:作为基于散列集合定义键的散列值,如:HashSet<T>,Dictionary<K,V>容器等 (2 ...

  6. windows7命令帮助大全

    有关某个命令的详细信息,请键入 HELP 命令名ASSOC 显示或修改文件扩展名关联.ATTRIB 显示或更改文件属性.BREAK 设置或清除扩展式 CTRL+C 检查.BCDEDIT 设置启动数据库 ...

  7. Java NIO概述

    Java NIO 由以下几个核心部分组成: Channels Buffers Selectors 虽然 Java NIO 中除此之外还有很多类和组件,但在我看来,Channel,Buffer 和 Se ...

  8. bootstrap(关于栅格布局)

    栅格系统是通过行(.row)与列(column)的组合一起来创建页面布局的,所以只有列(column)可以作为行(row)的直接子元素,我们所要写的内容可以放在列里(column),不过在行的外层还需 ...

  9. iosselect:一个js picker项目,在H5中实现IOS的下拉效果

    iosselect是在webapp下的一个picker组件,可以轻松实现各类选择器效果.比如地区选择 时间选择 日期选择等. 下面是一个地址选择器demo截图,可以访问:http://zhoushen ...

  10. BFC深入理解

    BFC 在上一篇文章中,清除浮动方法解析,我们谈及了一些使用css属性解决浮动带来的影响.但是在解决浮动带来的影响的方法中,如果细心思考,会产生如下疑问: 为什么overflow可以清除浮动带来的影响 ...