在排序数组中查找元素的第一个和最后一个位置
1.自解
class Solution {
public int[] searchRange(int[] nums, int target) {
int[] index = new int[2];
int len = nums.length;
if (len == 0) {
index[0] = -1;
index[1] = -1;
return index;
}
int left = 0;
int right = len - 1;
while(left < right) {
int middle = (left + right) / 2;
if (nums[middle] > target) {
right = middle - 1;
} else if (nums[middle] < target) {
left = middle + 1;
} else {
right = middle;
}
}
int start = -1;
if (nums[left] == target) {
start = left;
index[0] = start;
} else {
index[0] = -1;
index[1] = -1;
return index;
}
left = 0;
right = len - 1;
while(left < right) {
int middle = (left + right + 1) / 2;
if (nums[middle] > target) {
right = middle - 1;
} else if (nums[middle] < target) {
left = middle + 1;
} else {
//两套模板,这里使用left = middle而不是left = middle +1 是因为将已找到的纳入搜索范围,做兜底使用
left = middle;
}
}
if (nums[left] == target) {
index[1] = left;
}
return index;
}
}
2.更牛的解法
target的第一个左边必然是target最后一个
class Solution {
//先找>=target的第一个
//再找>target的第一个
//我真是这辈子都不想看见这题
public int[] searchRange(int[] nums, int target) {
int l=search(nums,target);
int r=search(nums,target+1);
if(l==nums.length||nums[l]!=target)
return new int[]{-1,-1};
return new int[]{l,r-1};
}
//找>=target的第一个
public int search(int[] nums,int target){
int l=0,r=nums.length;
while(l<r){
int mid=(r+l)>>1;
if(nums[mid]>=target)
r=mid;
else
l=mid+1;
}
return l;
}
}
3.二分模板知识巩固
3.1.二分模板:
int bsearch_1(int l, int r)
{
while (l < r)
{
int mid = (l + r)/2;
if (check(mid)) r = mid;
else l = mid + 1;
}
return l;
}
int bsearch_2(int l, int r)
{
while (l < r)
{
int mid = ( l + r + 1 ) /2;
if (check(mid)) l = mid;
else r = mid - 1;
}
return l;
}