二分查找是一个基础的算法,也是面试中常考的一个知识点。二分查找就是将查找的键和子数组的中间键作比较,如果被查找的键小于中间键,就在左子数组继续查找;如果大于中间键,就在右子数组中查找,否则中间键就是要找的元素。
基本概念:
二分查找也称折半查找(Binary Search),它是一种效率较高的查找方法。但是,折半查找要求线性表必须采用顺序存储结构,而且表中元素按关键字有序排列。
查找过程:
首先,假设表中元素是按升序排列,将表中间位置记录的关键字与查找关键字比较,如果两者相等,则查找成功;否则利用中间位置记录将表分成前、后两个子表,如果中间位置记录的关键字大于查找关键字,则进一步查找前一子表,否则进一步查找后一子表。重复以上过程,直到找到满足条件的记录,使查找成功,或直到子表不存在为止,此时查找不成功。
算法要求:
1.必须采用顺序存储结构。
2.必须按关键字大小有序排列。
代码演示:
/**
* 二分查找,找到该值在数组中的下标,否则为-1
*/
static int binarySearch(int[] arr,int num) {
int left = 0;
int right = arr.length - 1;
while(left <= right){
int median = (left + right) / 2; //中间值
if(arr[median] == num ) {
return median;
}else if(arr[median] < num) {
left = median + 1;
}else {
right = median - 1;
}
}
//如果没找到就返回-1;
return -1;
}
测试:
public static void main(String[] args) {
int[] obj = {1,3,3,5,7,9,56,89,444,999};
//注意:此时只会返回第一个要查找的数字
System.out.println(binarySearch(obj,3)); //结果为:1
}
}
查找最后一个与key相等的元素:
/**
* 查找最后一个与key相等的元素
*/
static int findLastResult(int[] arr, int num) {
int left = 0;
int right = arr.length - 1;
while (left <= right) {
int median = (left + right) / 2; // 中间值
if (arr[median] <= num) {
left = median + 1;
} else {
right = median - 1;
}
}
if (right >= 0 && arr[right] == num) {
return right;
}
return -1;
}
测试:
public static void main(String[] args) {
int[] obj = {1,3,3,5,7,9,56,89,444,999};
System.out.println(findLastResult(obj, 7)); //此时结果为4
}
}
二分查找变种较多,不过它们的“套路”是一样的,如何快速写出二分查找的代码,只需按照以下步骤即可:
1 首先判断出是返回left,还是返回right
因为我们知道最后跳出while (left <= right)循环条件是right < left,且right = left - 1,
最后right和left一定是卡在"边界值"的左右两边,如果是比较值为key,查找小于等于(或者是小于)key的元素,则边界值就是等于key的所有元素的最左边那个,其实应该返回left。
2 判断出比较符号
如果是查找小于等于key的元素,则知道应该使用判断符号>=,因为是要返回left,所以如果array[mid]等于或者大于key,就应该使用>=,以下是总结公式:
while (left <= right) {
int mid = (left + right) / 2;
if (array[mid] ? key) {
//... right = mid - 1;
}
else {
// ... left = mid + 1;
}
}
return xxx;
如有错误,欢迎指点~
参考:https://www.cnblogs.com/luoxn28/p/5767571.html