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
.
这道题是在给定二维数组中查找目标值,题目难度为Medium。
每行都已排好序并且每行第一个数字大于上一行最后一个数字,也就是说整个二维数组是排好序的,可以将整个二维数组看做一维数组来进行二分查找,具体代码:
class Solution {
public:
bool searchMatrix(vector<vector<int>>& matrix, int target) {
if(matrix.empty() || matrix[0].empty()) return false;
int row = matrix.size(), col = matrix[0].size();
int bgn = 0, end = row*col-1, mid;
while(bgn <= end) {
mid = (bgn + end) / 2;
if(matrix[mid/col][mid%col] == target) return true;
else if(matrix[mid/col][mid%col] > target) end = mid - 1;
else bgn = mid + 1;
}
return false;
}
};
还可以先根据每行的第一个数字做二分查找来确定目标值可能存在的行,然后再在该行做二分查找来确定目标值是否存在,具体代码:
class Solution {
public:
bool searchMatrix(vector<vector<int>>& matrix, int target) {
if(matrix.empty() || matrix[0].empty()) return false;
int bgn = 0, end = matrix.size()-1, mid;
while(bgn <= end) {
mid = (bgn + end) / 2;
if(matrix[mid][0] == target) return true;
else if(matrix[mid][0] < target) bgn = mid + 1;
else end = mid - 1;
}
if(bgn == 0) return false;
int row = bgn - 1;
bgn = 0;
end = matrix[row].size()-1;
while(bgn <= end) {
mid = (bgn + end) / 2;
if(matrix[row][mid] == target) return true;
else if(matrix[row][mid] < target) bgn = mid + 1;
else end = mid - 1;
}
return false;
}
};
第一种方法时间复杂度O(log(m*n)),第二种方法时间复杂度O(log(m)+log(n)),两种方法时间复杂度是一样的。