搜索二维矩阵
题目
给你一个满足下述两条属性的 m x n
整数矩阵:
- 每行中的整数从左到右按非递减顺序排列。
- 每行的第一个整数大于前一行的最后一个整数。
给你一个整数 target
,如果 target
在矩阵中,返回 true
;否则,返回 false
。
MyAns
class Solution {
public:
bool searchMatrix(vector<vector<int>>& matrix, int target) {
int high = matrix.size();
if (high==0)return false;
int weith = matrix[0].size();
int l=0,r=high-1,mid,sign;
while(l<=r){
mid = (r-l)/2+l;
if(matrix[mid][weith-1]<target)l=mid+1;
else r=mid-1;
}
sign = l;
if(sign>=high)return false;
l=0;r=weith-1;
while(l<=r){
mid = (r-l)/2+l;
if(matrix[sign][mid]<target)l=mid+1;
else if (matrix[sign][mid]==target)return true;
else r=mid-1;
}
return false;
}
};
两次二分即可,注意选矩阵每列最末尾数字进行第一次二分,离散数学可能会用到
*搜索旋转排序数组
题目
整数数组 nums
按升序排列,数组中的值 互不相同 。
在传递给函数之前,nums
在预先未知的某个下标 k
(0 <= k < nums.length
)上进行了 旋转,使数组变为 [nums[k], nums[k+1], ..., nums[n-1], nums[0], nums[1], ..., nums[k-1]]
(下标 从 0 开始 计数)。例如, [0,1,2,4,5,6,7]
在下标 3
处经旋转后可能变为 [4,5,6,7,0,1,2]
。
给你 旋转后 的数组 nums
和一个整数 target
,如果 nums
中存在这个目标值 target
,则返回它的下标,否则返回 -1
。
你必须设计一个时间复杂度为 O(log n)
的算法解决此问题。
Code
一开始的思路是先找到断层点,化简成普通升序数组搜索问题。废了九牛二虎之力也没写出来,最后抄了答案。
class Solution {
public:
int search(vector<int>& nums, int target) {
int length = nums.size();
if (length == 0)return -1;
int l=0,r=length-1,mid=(r-l)/2+l;
if(length==0)return-1;
if(length==1)return nums[0] == target ? 0 : -1;
while(l<=r){
mid=(r+l)/2;
if(nums[mid]==target)return mid;
if(nums[mid]>=nums[0]){
if(target<nums[mid]&&target>=nums[0])r=mid-1;
else l = mid+1;
}else if(nums[mid]<nums[0]){
if(target>nums[mid]&&target<=nums[length-1])l=mid+1;
else r=mid-1;
}
}
return -1;
}
};
- 判断mid在断层左边还是右边
- 判断下一个循环选mid左半边还是右半边
总的来说,每次判断都是可以列举的,做四次判断即可。