基础版方法实现
//基础版本内j索引参与查找
public static int Search(int target, int[] arr) {
int i = 0, j = arr.length - 1;
while (i <= j) {
//移位操作符取中间索引以防以为操作数超出int范围产生负数索引
int mid = (i + j) >>> 1;
if (arr[mid] == target) {
return mid;
}
//目标值小于中间值,继续向左寻找
else if (target < arr[mid]) {
j = mid - 1;
}
//目标值大于中间值,继续向右寻找
else if (arr[mid] < target) {
i = mid + 1;
}
}
return -1;
}
改进版方法实现
//改进版本内j索引不参与查找
public static int Search(int target, int[] arr) {
int i = 0, j = arr.length; //j的初始值超出最大索引,从最开始就不参与查找
//此处为i<j,若条件为i<=j则查找后期会出现死循环
while (i < j) {
//移位操作符取中间索引以防以为操作数超出int范围产生负数索引
int mid = (i + j) >>> 1;
if (arr[mid] == target) {
return mid;
}
//目标值小于中间值,继续向左寻找
else if (target < arr[mid]) {
j = mid; //mid索引对应元素已查找不符合要求,将j赋值为mid
}
//目标值大于中间值,继续向右寻找
else if (arr[mid] < target) {
i = mid + 1;
}
}
return -1;
}
二分查找平衡版:
平衡版本忽略了初始版目标元素在左右两侧查找次数不平衡的问题,减少了对元素与查找元素的比较,减少了判断次数
public static int binarySearch3(int[] arr, int target){
//定义初末索引位置,j索引对应元素不取
int i = 0, j = arr.length;
//j - i < 1即意味着待查找元素个数,若待查找元素个数为1时i即为对应索引,此时跳出循环进行判断
while(j - i > 1){
int m = (i + j) >>> 1;
if(arr[m] > target){
j = m;
}
//进入else条件为arr[m]<=target,则m索引对应元素可能为目标元素,不可跳过
else {
i = m;
}
}
//剩余个数为一,进行判断
if(arr[i] == target){
return i;
}
else{
return -1;
}
}
查找重复元素最左侧元素
//寻找最靠左的查找元素
public static int binarySearch(int[] arr, int key){
//使没寻找到元素最后返回-1
int candidate = -1;
int i = 0, j = arr.length - 1, mid = 0;
while(i <= j){
mid = (i + j) >>> 1;
if(arr[mid] < key){
i = mid + 1;
}
else if(key < arr[mid]){
j = mid - 1;
}
else{
//将此时查找到的索引值赋值给变量待选
candidate = mid;
//继续查找左侧元素
j = mid - 1;
}
}
return candidate;
}
查找重复元素最右侧元素
//寻找最靠右的查找元素
public static int binarySearch(int[] arr, int key){
//使没寻找到元素最后返回-1
int candidate = -1;
int i = 0, j = arr.length - 1, mid = 0;
while(i <= j){
mid = (i + j) >>> 1;
if(arr[mid] < key){
i = mid + 1;
}
else if(key < arr[mid]){
j = mid - 1;
}
else{
//将此时查找到的索引值赋值给变量待选
candidate = mid;
//继续查找左侧元素
i = mid + 1;
}
}
return candidate;
}
求排名、前后任、最近邻居
查找重复元素最左侧元素返回值改动版:
//寻找最靠左的查找元素
public static int binarySearch(int[] arr, int key){
int i = 0, j = arr.length - 1, mid = 0;
while(i <= j){
mid = (i + j) >>> 1;
if(arr[mid] < key){
i = mid + 1;
}
//若目标值恰好等于中间值或在中间值左侧,继续向左寻找
else if(key <= arr[mid]){
j = mid - 1;
}
}
//返回大于等于待查找元素最左侧的元素的索引值
return i;
}
查找重复元素最右侧元素返回值改动版:
//寻找最靠右的查找元素
public static int binarySearch(int[] arr, int key){
int i = 0, j = arr.length - 1, mid = 0;
while(i <= j){
mid = (i + j) >>> 1;
if(arr[mid] <= key){
i = mid + 1;
}
else if(key < arr[mid]){
j = mid - 1;
}
}
//返回小于等于待查找元素的最靠右的元素索引
return j;
}

被折叠的 条评论
为什么被折叠?



