一、二分查找
1)、查找的数组或者集合必须是有序的,倒序或者升序均可。
2)、实现思路是:将需要查找的集合或者数组对半均分,每次循环只需要对比数组中间位置的Value是否大于需要查找的Value,大于则取前半部分小于就取后半部分。
3)、数组或者集合中可能存在重复元素,按照以下逻辑无法完全找到所有该Value对应下标。
(1):可以考虑循环将已经找的下标向左或者向右+1获取对应Value再做对比,直到找完所有重复元素下标
(2):如果对数据要求没有那么高,可以考虑使用Set集合去除重复元素排序之后,再做查找
/**
* 循环实现二分查找
* @param a
* @param val
* @return
*/
public static int binarySearch(int[] a,int val) {
if(a.length <= 0) {
return -1;
}
int lo = 0;//开始下标位置
int hi = a.length-1;//最高下标位置,取最后一位
while(lo <= hi) {//当 lo <= hi时,证明该数组里面已经查询完成
int temp = lo + (hi - lo)/2;//获取数组中间的下标位置
//如果当前查询val大于数组中间值则开始的下标向右边移动变成(lo = temp+1)中间下标对应的值不进入下次循环
if(val > a[temp] ) {
lo = temp+1;
//如果当前查询val小于数组中间值则最高位置的下标向左边移动变成(hi = temp-1)中间下标对应的值不进入下次循环
}else if(val < a[temp]) {
hi = temp -1;
}else {
//相等就返回当前的下标
return temp;
}
}
return -1;
}
/**
* 递归实现二分查找
* @param arr
* @param lo
* @param hi
* @param val
* @return
*/
public static int binarySearch(int[] arr,int lo,int hi,int val) {
if(arr.length == 0) {
return -1;
}
if(lo <= hi) {
int mid = lo + (hi - lo)/2;
if(val > arr[mid]) {
return binarySearch(arr,mid+1,hi,val);
}else if(val < arr[mid]) {
return binarySearch(arr,lo,mid-1,val);
}else {
return mid;
}
}else {
return -1;
}
}