Java二分查找(普通方法和递归方法)

最近也我闲下来的时候看一些算法书籍,去解决一些算法问题。我会将常见的算法以记录的方式放在这里,以供我后续查找,也以这种方式分享给大家!我将把参透的代码做大量注释,尽可能做到每一行代码都简单易懂!


二分查找也称折半查找(Binary Search),它是一种效率较高的查找方法。但是,折半查找要求线性表必须采用顺序存储结构,而且表中元素按关键字有序排列。

要求

  • 必须采用顺序存储结构。
  • 必须按关键字大小有序排列。

复杂度分析:O(logN)

什么是二分查找?举例说明(小故事哦!)


在这里插入图片描述


小明喜欢小红,于是和小红就表白了。小红这么说:“我们玩个游戏吧,我心里想一个从1 ~ 100的数字并记下来,你如果在10次之内猜到我心里记下的那个数字,我就和你在一起!”。

于是,小明就有一个猜想。

如果开始我猜100的一半也就是50。不管是猜小了还是猜大了,都排除了50个数字。如果猜小了,我下次就继续猜50 ~ 100的中间数,也就是二分数。这样以来,小明利用他的这个猜想猜了几次就猜中了小红心中记起的数字,并获得了小红的芳心。

如果我们遍历这些数字逐个猜的话,那岂不是很麻烦,而且还浪费时间,二分查找就帮小明解决了这个棘手的问题!

那么如果列表中包含40亿个数字,遍历起来可就更麻烦了,而二分查找只需要猜32次就OK!所谓小知识大作为!

不得不说我自己编的这个故事真的很生动形象。(允许我自恋一下哈!)


这就是二分查找,每次猜测的数字的个数以排除的方式呈现出来!如图:(最多7步完成)

在这里插入图片描述
手残党也能画图,在线画图工具:https://www.processon.com


OK!懂了二分查找的原理,那么我就直接上代码了!(第一种是原方案,第二种是递归)

/** 
* @author Ziph
* @date 2020年3月1日
* @Email mylifes1110@163.com
* @param key 查找元素
* 
* 二分查找
*/
public class TestBinarySearch {
	public static void main(String[] args) {
		int[] a = new int[] {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
		System.out.println(binarySearch(a, 5));
	}
	
	public static int binarySearch(int array[], int key) {
		int mid = array.length / 2;//中间长度的位置
		
		//如果key正好在数组中间的位置返回其位置(数组下标)
		if (key == array[mid]) {
			return mid;
		}
		
		//头部也就是开始的:第一个数组元素,数组下标为0
		int head = 0;
		
		//尾部也就是结束的:最后一个数组元素,数组下标为array.length-1
		int tail = array.length - 1;
		
		//利用二分查找的特性去循环查找key值
		while (head <= tail) {//只要范围没有缩小到只剩下一个元素就继续循环下去
			mid = (tail + head) / 2;//每次循环检查中间数组下标mid
			if (key < array[mid]) {//猜的数大了
				tail = mid - 1;
			} else if (key > array[mid]) {//猜的数小了
				head = mid + 1;
			} else {
				return mid;
			}
		}
		return -1;//如果数组中没有key值,则返回-1
	}
}

递归的做法

/** 
* @author Ziph
* @date 2020年3月1日
* @Email mylifes1110@163.com
* @param key 查找元素
* 
* 二分查找(递归)
*/
public class TestBinarySearch {
	public static void main(String[] args) {
		int[] a = new int[] {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
		System.out.println(recursionBinarySearc(a, 0, a.length - 1, 5));
	}
	
	public static int recursionBinarySearc(int array[], int head, int tail, int key) {
		int mid = (head + tail) / 2;
		
		if (array[mid] == key) {
			return mid;
		}
		
		if (head >= tail) {//递归出口
			return -1;
		} else if (key < array[mid]) {
			return recursionBinarySearc(array, head, mid - 1, key);
		} else if (key > array[mid]) {
			return recursionBinarySearc(array, mid + 1, tail, key);
		}
		return -1;
	}
}

 
 
结果:当key=5时,返回的都是4(数组下标)
 
 

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值