LeetCode 热题 100 74. 搜索二维矩阵
LeetCode 热题 100 | 74. 搜索二维矩阵
大家好,今天我们来解决一道经典的算法题——搜索二维矩阵。这道题在 LeetCode 上被标记为中等难度,要求我们在一个满足特定条件的二维矩阵中查找一个目标值。如果目标值在矩阵中,返回 true
;否则,返回 false
。下面我将详细讲解解题思路,并附上 Python 代码实现。
问题描述
给定一个满足以下两个条件的 m x n 整数矩阵:
- 每行中的整数从左到右按非严格递增顺序排列。
- 每行的第一个整数大于前一行的最后一个整数。
你需要判断一个整数 target
是否在矩阵中。
示例 1:
输入:matrix = [[1,3,5,7],[10,11,16,20],[23,30,34,60]], target = 3
输出:true
示例 2:
输入:matrix = [[1,3,5,7],[10,11,16,20],[23,30,34,60]], target = 13
输出:false
解题思路
核心思想
-
二分查找:
- 由于矩阵的每一行都是有序的,并且每行的第一个元素大于前一行的最后一个元素,整个矩阵可以看作是一个一维有序数组。
- 因此,可以使用二分查找来高效地查找目标值。
-
映射二维索引到一维索引:
- 将二维矩阵的索引映射到一维数组的索引,方便进行二分查找。
Python代码实现
def searchMatrix(matrix, target):""":type matrix: List[List[int]]:type target: int:rtype: bool"""if not matrix or not matrix[0]:return Falsem, n = len(matrix), len(matrix[0]) # 获取矩阵的行数和列数left, right = 0, m * n - 1 # 初始化二分查找的左右边界while left <= right:mid = (left + right) // 2 # 计算中间索引mid_value = matrix[mid // n][mid % n] # 将一维索引映射到二维索引if mid_value == target:return True # 找到目标值,返回 Trueelif mid_value < target:left = mid + 1 # 目标值在右侧,移动左边界else:right = mid - 1 # 目标值在左侧,移动右边界return False # 未找到目标值,返回 False# 测试示例
print(searchMatrix([[1,3,5,7],[10,11,16,20],[23,30,34,60]], 3)) # 输出: True
print(searchMatrix([[1,3,5,7],[10,11,16,20],[23,30,34,60]], 13)) # 输出: False
代码解析
-
初始化边界:
left
初始化为 0,right
初始化为矩阵的最后一个元素的索引m * n - 1
。
-
二分查找:
- 在
left <= right
的范围内,计算中间索引mid
。 - 将一维索引
mid
映射到二维索引matrix[mid // n][mid % n]
。 - 如果
mid_value
等于目标值,直接返回True
。 - 如果
mid_value
小于目标值,说明目标值在右侧,将left
移动到mid + 1
。 - 如果
mid_value
大于目标值,说明目标值在左侧,将right
移动到mid - 1
。
- 在
-
返回结果:
- 如果未找到目标值,循环结束后返回
False
。
- 如果未找到目标值,循环结束后返回
复杂度分析
- 时间复杂度:O(log(m * n)),其中
m
是矩阵的行数,n
是矩阵的列数。二分查找的时间复杂度为 O(log(m * n))。 - 空间复杂度:O(1),只使用了常数个额外空间。
示例运行
示例 1
输入:matrix = [[1,3,5,7],[10,11,16,20],[23,30,34,60]], target = 3
输出:true
示例 2
输入:matrix = [[1,3,5,7],[10,11,16,20],[23,30,34,60]], target = 13
输出:false
总结
通过将二维矩阵的索引映射到一维索引,我们可以使用二分查找高效地查找目标值。这种方法不仅简洁,而且效率非常高,适合处理类似的问题。希望这篇题解对大家有所帮助,如果有任何问题,欢迎在评论区留言讨论!
关注我,获取更多算法题解和编程技巧!