Leetcode[二分查找] 74. 搜索二维矩阵

Leetcode[二分查找] 74. 搜索二维矩阵

审题

编写一个高效的算法来判断 m x n 矩阵中,是否存在一个目标值。该矩阵具有如下特性:
每行中的整数从左到右按升序排列。
每行的第一个整数大于前一行的最后一个整数。
 

示例 1:
输入:matrix = [[1,3,5,7],[10,11,16,20],[23,30,34,50]], target = 3
输出:true

示例 2:
输入:matrix = [[1,3,5,7],[10,11,16,20],[23,30,34,50]], target = 13
输出:false

示例 3:
输入:matrix = [], target = 0
输出:false
 
提示:
m == matrix.length
n == matrix[i].length
0 <= m, n <= 100
-10^4 <= matrix[i][j], target <= 10^4

看到这道题,首先想到用二分,然而,却有可能对于一些数的判断和边界条件产生不同的影响,实现起来细节较多,多次WA之后,好歹算是AC了,但是代码依旧不尽人意,具体实现方法是先用二分查找看待寻找数据在哪行,再用二分查找在该行找到该数。

代码实现

方案一(上文提到的方法):

WA了好几次,有蒙的嫌疑,大家看个乐呵就行。

class Solution {
public:
    int find_row(vector<vector<int>>& matrix, int target) {
        int l=0;
        int r=matrix.size()-1;
        int mid;

        if ( r == 0 ) return 0;
        
        while ( l<=r ) {
            mid = l + (r-l)/2;
            if ( target == matrix[mid][0] ) return mid;
            if ( target < matrix[l][0] ) return (l-1)<0?0:l-1;
            if ( target > matrix[r][0] ) return r;
            if ( target > matrix[mid][0] ) l = mid + 1;
            else r = mid - 1;
        }
        return -1;
    }
    bool searchMatrix(vector<vector<int>>& matrix, int target) {
        if ( matrix.size() == 0 ) return false;
        if ( matrix[0].size() == 0 ) return false;
        
        int l=0;
        int r=matrix[0].size()-1;
        int mid;
        int row = find_row(matrix, target);
        while ( l<=r ) {
            mid = l + (r-l)/2;
            if ( matrix[row][mid] == target ) return true;
            if ( matrix[row][mid] < target ) l = mid+1;
            else r = mid-1;
        }
        return false; 
    }
};

方案2(一维数组):

呜呜呜,我怎么那么菜啊,二维数组完全可以当作一维数组来从左往右找,这就是最基本的二分查找,下次还是要好好想想数据结构,这也太顶了。换个数据结构秒变简单题:

class Solution {
public:
    bool searchMatrix(vector<vector<int>>& matrix, int target) {
        int m = matrix.size();
        if ( m == 0 ) return false;
        int n = matrix[0].size();
        int l=0;
        int r=m*n-1;
        int mid;
        while ( l<=r ) {
            mid = l + (r-l)/2;
            if ( matrix[mid/n][mid%n] == target ) return true;
            if ( matrix[mid/n][mid%n] > target ) r = mid-1;
            else l = mid+1;
        }
        return false;
    }
};

反思

这道题的话,看出来了审题的重要性吧还是,好好审题比啥都强,这道题的难度一般,一维数组确实是挺巧的,学习了,巧巧巧。

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值