[Leetcode]Search a 2D Matrix

本文介绍了一种高效的算法用于在具有特定排列属性的二维矩阵中查找元素,通过逐行和逐列的筛选来减少搜索范围,从而实现时间复杂度为O(m+n)的查找过程。进一步介绍了优化算法,将时间复杂度降低至O(logm+logn),并讨论了一种将二维矩阵视为一维数组进行二分查找的方法,其复杂度同样为O(log(m*n))。

Write an efficient algorithm that searches for a value in an m x n matrix. This matrix has the following properties:

  • Integers in each row are sorted from left to right.
  • The first integer of each row is greater than the last integer of the previous row.

For example,

Consider the following matrix:

[
  [1,   3,  5,  7],
  [10, 11, 16, 20],
  [23, 30, 34, 50]
]

Given target = 3, return true.

在一个二维的矩阵里查找某个元素是否存在~矩阵每一行都是有序的,并且下一行的第一个元素值比这行的最后一个元素值大~

记得貌似在剑指offer这本书里看到过一个类似的题,那道题里矩阵的每行每列也都是是有序的,但不保证下一行的第一个元素值比这行的最后一个元素值大,思路是采取右上角的一个数字,与target比较,如果相同的话,返回True;如果右上角的值小于target,则target不可能在这一行里,可以把这一行剔除掉(维护两个index);如果值大于target,则说明target不可能在这一列,把这一列剔除掉;这样每一步都可以缩小查找的范围~算法时间复杂度应该是O(m+n)~   代码如下(写的时候对这题还有点印象,然后一次就AC了偷笑)

class Solution:
    # @param matrix, a list of lists of integers
    # @param target, an integer
    # @return a boolean
    def searchMatrix(self, matrix, target):
        if matrix is None or len(matrix) == 0 or len(matrix[0]) == 0: return False
        row, col = len(matrix), len(matrix[0])
        i, j = 0, col - 1
        while i < row and j >= 0:
            if matrix[i][j] == target:
                return True
            elif matrix[i][j] > target:
                j = j - 1
            else:
                i = i + 1
        return False

看了一下其他解法~在时间复杂度上还可以提升~可以进行两次二分查找,把时间复杂度改进为O(logm + logn)~先按行查找,定位到某行,然后再按列查找~代码如下(写的时候要注意一下第一个二分搜索, 容易出错)

class Solution:
    # @param matrix, a list of lists of integers
    # @param target, an integer
    # @return a boolean
    def searchMatrix(self, matrix, target):
        if matrix is None or len(matrix) == 0 or len(matrix[0]) == 0: return False
        rowLen, colLen = len(matrix), len(matrix[0])
        l, r = 0, rowLen - 1
        while l <= r:
            mid = l + (r - l) / 2
            if matrix[mid][0] == target: return True
            elif matrix[mid][0] > target: r = mid - 1
            else: l = mid + 1
        row = r 
        if row < 0: return False
        l, r = 0, colLen - 1 
        while l <= r:
            mid = l + (r - l) / 2
            if matrix[row][mid] == target: return True
            elif matrix[row][mid] > target: r = mid - 1
            else: l = mid + 1
        return False

还有另外一种解法,就是把2维矩阵当成一个1维的数组,然后在一维数组里用二分搜索查找~简化成的一维数组长度为rowLen * colLen; 中间值在二维矩阵里对应的是matrix[mid / colLen][mid % colLen]~ 时间复杂度是O(log(m*n)) = O(logm + logn),与进行两次二分搜索的复杂度一样~ 但有人认为这种解法还有一些缺陷:首先,m*n可能会溢出;其次,引进了大量的复杂运算:/ 和 % ~ (不过python 自带大数整数运算,整数不会溢出,只要内存足够)

class Solution:
    # @param matrix, a list of lists of integers
    # @param target, an integer
    # @return a boolean
    def searchMatrix(self, matrix, target):
        if matrix is None or len(matrix) == 0 or len(matrix[0]) == 0: return False
        rowLen, colLen = len(matrix), len(matrix[0])
        l, r = 0, rowLen * colLen - 1
        while l <= r:
            mid = l + (r - l) / 2
            midVal = matrix[mid / colLen][mid % colLen]
            if midVal == target: return True
            elif midVal < target:
                l = mid + 1
            else:
                r = mid - 1
        return False


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值