资讯动态

算法刷题记录 —— 盛最多水的容器

发布时间:2026/8/16 10:34:45 来源:尧图企业网站定制
题目链接11.盛最多水的容器问题分析这道题如果只追求O(n²)的实现并不难难点在于如何做到O(n)。我们先来看一下题目的示意图这道题的核心需求非常明确——找到能盛最多水的两条线构成的容器。容量的计算公式很简单面积 长 × 宽其中「宽」由两条线中较短的那条决定木桶效应「长」则是两条线在数组中的下标距离。换句话说对于任意两个位置i和jarea (j - i) × min(height[i], height[j])问题转化为如何快速找到「宽」和「长」的最佳搭配使得乘积最大化O(n²) 暴力解法最直接的思路当然是两重for循环枚举所有可能的线对组合逐一计算面积并更新最大值。代码写起来非常简单但时间复杂度是 O(n²)在数据量较大时会超时。那么为什么暴力解法是 O(n²) 呢原因在于每次只移动一个指针另一个指针固定不动要遍历出所有组合就必须做 n × n 级别的枚举。O(n) 双指针优化 —— 核心思路想要降到 O(n)思路也很直观两个指针都动起来。说起来简单但关键在于——怎么动才能保证不漏掉最大面积的那一组初始状态我们将left指针放在数组头部下标0right指针放在数组尾部下标n-1。此时「长」是最大的但「宽」可能很小——因为两条线中较矮的那条限制了容量。移动策略回到面积公式面积 长 × 宽。在当前状态下无论我们移动哪个指针「长」都会减小。那么我们要做的就是尽量让「宽」变大来弥补「长」的损失。而「宽」受限于两条线中较矮的那一条——根据木桶效应矮的那条才是真正的瓶颈。因此移动策略非常清晰如果height[left] height[right]说明左边的线是瓶颈那就left尝试换一条更高的线否则右边的线是瓶颈那就right--。每移动一步都重新计算当前面积并与全局最大值比较。当left和right相遇时遍历结束。为什么这样不会漏掉最大值因为每次我们舍弃的都是当前较矮的那条边——它和另一条边之间不可能再产生更大的面积了毕竟「长」在缩小而「宽」已经被这条矮边锁死了上限。这种贪心策略保证了我们一定能遍历到最优解。整个过程类似于滑动窗口本质上是一种巧妙的双指针 贪心思想。代码实现classSolution{publicintmaxArea(int[]height){intleft0;intrightheight.length-1;intmax0;while(left!right){// 计算当前面积长 × 宽intarea(right-left)*Math.min(height[left],height[right]);// 移动较短的那条边if(height[left]height[right]){left;}else{right--;}// 更新最大值if(areamax){maxarea;}}returnmax;}}关键点总结面积公式(right - left) × min(height[left], height[right])这是理解整个题目的基础。双指针初始化左右指针分别指向数组的头和尾此时「长」最大。移动策略每次移动较短的那条边这是「木桶效应」的直接体现也是 O(n) 正确性的核心保证。数学函数Math.min()用于获取两条边中的较小值注意积累这类常用 API。复杂度每个元素最多被访问一次时间复杂度O(n)空间复杂度O(1)。这道题的双指针思路非常经典核心在于想清楚「为什么移动较短的那条边不会漏掉最优解」。理解了这一点整道题就豁然开朗了。

读完文章,也想定制专属网站?

尧图设计师 24 小时内与您沟通定制方案

免费获取报价