二分查找和斐波那契查找优化

原创 2016年06月01日 15:15:44

二分查找是一种很高效的查找方法,它需要所要查找的数列有序,然后每次折半进行查找,时间复杂度为O(logn),

理解起来不难但是在代码实现要注意边界

template<typename T>
int binarySearch(T aim,T *array,int left,int right){
	if(left<right){
		int mid=(left+right)>>1;
		if(aim<array[mid]){
			//right=mid;
			binarySearch(aim,array,left,mid);
		}
		else if(array[mid]<aim){
			//left=mid+1;
			binarySearch(aim,array,mid+1,right);
		}
		else{
			return mid;
		}		
	}
	else
	return -1;
}

将原来的数组区间[left,right)分为3份[left,mid),mid,[mid+1,right),通过重点mid来判断目标值属于哪个区间,然后再进行判断。

二分查找的方法是尽量的将区间等分,保证查找结构一个左右子树等高的树,但是通过分析上面代码可以知道,在左区间查找需要进行一次判断,在右区间进行查找需要进行两次判断,很明显若想让代码平均耗时减少,应保证目标值在左区间。所以应将原来的区间分为左区间大于又区间,通过证明知道采用黄金分割(斐波那数列)进行分割会较少时间复杂度

要用斐波那搜索,需要的前提条件是:数列有序,以及初始数列的长度加1是斐波那数。注意是数列长度fib[k]-1才行

所以首先应判断数列长度是不是某个fib-1才行

vector<int>fib;

int placeInFibonacci(int num){
	if(fib.size()<2){
		fib.push_back(0);
		fib.push_back(1);
	}
	for(int i=2;;++i){
		if(fib.size()==i){
			fib.push_back(fib[i-2]+fib[i-1]);
		}
		if(num==fib[i])
		return i;
		if(num<fib[fib.size()-1])
		return -1;
	}
}
template<typename T>
int fibonacciSearch(T aim,T *array,int left,int right){
	int k=placeInFibonacci(right+1);
	if(k==-1){
		return -1;	
	}
	while(left<right){
		int mid=fib[k-1]-1+left;
		if(aim<array[mid]){
			right=mid;
			--k;
		}
		else if(array[mid]<aim){
			left=mid+1;
			k-=2;
		}
		else{
			return mid;
			
		}		
	}
	return -1;
}

以上是数列中不含有重复的数当含有重复的数字的时候,若要返回最后一个数字的位置,则需要进行如下修改

template<typename T>
int binarySearch(T aim,T *array,int left,int right){
	while(left<right){
		int mid=(left+right)>>1;
		if(aim<array[mid]){
			right=mid;
		}
		else if(array[mid]<aim){
			left=mid+1;
		}
		else{
			while(aim==array[++mid]);
			return --mid;
		}		
	}
	return -1;
}


版权声明:本文为博主原创文章,未经博主允许不得转载。

“斐波那契查找”真的比“二分查找”快么?

Is Fibonacci Search really "faster" than Binary Search? 申明:本文讨论的搜索对象为有序数组,不是数学上讨论的函数。 ...

斐波那契查找详解

斐波那契查找的前提是待查找的查找表必须顺序存储并且有序。     相对于折半查找,一般将待比较的key值与第mid=(low+high)/2位置的元素比较,比较结果分三种情况      1)相等,mi...

使用winSCP+putty发布项目至远程服务器

工具 ① winSCP ② putty 1.1 winSCP 1.1.1 什么是winSCP WinSCP 是一个 Windows 环境下使用的 SSH 的开源图形化 SFTP 客户端。同时...

二分查找的改进--差值查找

差值查找 在二分查找中,我们每次比较都可以排除一半的数据量,这个已经是很高效了。如果利用关键字本身的信息,每次排除的数据量充分依赖于关键字的大小,则查找会更高效,这就是差值查找的思想。 下面通...

查找(顺序查找、插值查找和斐波那契查找)

查找 查找定义:根据给定的某个值,在查找表中确定一个其关键字等于给定值的数据元素(或记录)。 查找表分类:静态查找表和动态查找表。 动态查找表:在查找过程中同时插入查找表中不存在的数据元素,或者...

折半查找、插值查找和斐波那契查找

一、折半查找
  • cdu09
  • cdu09
  • 2014年04月07日 21:32
  • 1912

考研路_数据结构_查找2_插值查找和斐波那契查找

数据结构常用查找算法_插值查找 在考研路_数据结构_查找1中,我们发现,二分查找每次都是从中间开始查找,若我们查找的关键值是靠近上区间或下区间,则二分查找效率有待提高。 从而我们考虑修改的代码为:...

时间空间复杂度(二分查找和斐波那契数列)

时间复杂度 空间复杂度 折半查找 斐波那契数列 递归法

“斐波那契查找”真的比“二分查找”快么?

Is Fibonacci Search really "faster" than Binary Search? 申明:本文讨论的搜索对象为有序数组,不是数学上讨论的函数。 1. 介绍 ...
  • fovwin
  • fovwin
  • 2013年06月11日 22:20
  • 4527
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:二分查找和斐波那契查找优化
举报原因:
原因补充:

(最多只允许输入30个字)