两端收缩最优解!LeetCode11题盛最多水的容器,双指针巧妙解题
2024-02-20 09:55:06
盛最多水的容器:双指针法的巧妙应用
在日常生活中,我们常常会遇到各种各样的容器,例如水杯、水桶和水缸。这些容器的形状各不相同,大小不一,但它们都有一个共同的特点,那就是都可以用来盛水。
想象一下,你有一个长方形的容器,它的长度和宽度都是固定的,但它的高度可以改变。现在,你需要调整它的高度,让它盛放最多的水。
盛最多水的容器问题
这个问题被称为“盛最多水的容器”问题,也是 LeetCode 上一道经典的面试题。它如下:
给你 n 个非负整数 a1
, a2
, ..., an
,每个数代表坐标系中一个点 (i, ai)
。在坐标系中画 n 条垂直线,垂直线 i
的两个端点分别为 (i, ai)
和 (i, 0)
。你的任务是找到两条垂直线,使得它们与 x 轴围成的容器可以盛放最多的水。
双指针法:一种巧妙的解决方案
这道题看似复杂,但其实可以使用一种非常简单的方法来解决,那就是双指针法。双指针法的基本原理是,使用两个指针分别指向数组的开头和结尾,然后同时向中间移动。
在移动过程中,比较两个指针指向的元素,选择较大的元素作为容器的高度,并计算当前容器的盛水量。如果当前容器的盛水量大于之前计算出的最大盛水量,则更新最大盛水量。
重复上述步骤,直到两个指针相遇,此时我们找到了可以盛放最多水的容器。
代码示例(Python)
def max_area(height):
"""
:param height: list[int]
:return: int
"""
left, right = 0, len(height) - 1
max_area = 0
while left < right:
area = min(height[left], height[right]) * (right - left)
max_area = max(max_area, area)
if height[left] < height[right]:
left += 1
else:
right -= 1
return max_area
if __name__ == "__main__":
height = [1, 8, 6, 2, 5, 4, 8, 3, 7]
print(max_area(height)) # 输出:49
复杂度分析
- 时间复杂度:O(n),其中 n 是数组
height
的长度。 - 空间复杂度:O(1),因为我们只需要两个指针来存储当前容器的高度。
总结
双指针法是一种非常强大的算法,可以用来解决各种不同的问题。掌握了双指针法,可以让你在面试中脱颖而出,也能让你在工作中更加游刃有余。
常见问题解答
-
为什么双指针法可以解决这个问题?
因为双指针法确保了我们始终考虑最大的容器高度,从而使我们能够找到盛放最多水的容器。
-
为什么在比较指针时,选择较大的元素作为容器高度?
因为较大的元素代表容器的更高的一边,这可以盛放更多的水。
-
为什么在计算面积时,要乘以
(right - left)
?(right - left)
代表容器的宽度,它与高度相乘,可以得到容器的面积。 -
为什么在更新最大面积时,要使用
max
函数?max
函数确保了我们始终保留最大的面积,从而找到盛放最多水的容器。 -
双指针法还能解决哪些其他问题?
双指针法还可以解决诸如查找子数组和、滑动窗口最大值等其他问题。