斐波那契查找

斐波那契查找

个人理解

一个很神奇的算法

前提:有序序列

之前我们的二分查找法,是和中间值比较的。那?

可不可以比较个别的呢?

比如,性感的黄金比例分割点?

在这里插入图片描述

正好研究数学的那群人又研究了个很神奇的数列
[1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144, 233, 377, 610, 987, 1597, 2584, 4181, 6765…]
它有这样的规律: F(k)=F(k-1)+F(k-2)
然后相邻的两个呢,又是基本符合黄金比例的(怎么样,惊不惊喜,我也不明白咋回事)
这么着就找到个相应的黄金比例分割点了

然后就是比较了,和以前一样,关键值小于比较值,最大的索引变到关键值对应的左边继续找。大于的话最小值变化到右边。

唯一有点意思的在于找黄金比例分割点

如果关键值在左边的话,无非就是往前面倒腾到上一个黄金比例分割点。右边的话,需要把握一下 F(k)=F(k-1)+F(k-2)这个小技巧了。

说明F(k)-F(k-1)=F(k-2),两个差的黄金比例分割点的值=最小值+等于往前倒腾两个的值

具体的过程不详细阐述,都在代码里了

代码实现之

package search;

import java.util.Arrays;

public class FibonacciSearch
{

	static int maxsize = 20;
	static int[] fib = new int[maxsize];

	// 斐波那契查找
	public static void main(String[] args)
	{
		int[] arr =
		{0, 1, 2, 3, 4, 5, 6, 7, 8, 9,10 };
		int index = fibSearch(arr, 10);
		System.out.println(index);
	}

	public static void fib()
	{
		fib[0] = 1;
		fib[1] = 1;
		for (int i = 2; i < maxsize; i++)
		{
			fib[i] = fib[i - 1] + fib[i - 2];
		}
//		System.out.println(Arrays.toString(fib));
//		System.out.println("--------------------");

	}

	public static int fibSearch(int[] arr, int key)
	{
		int k = 0;
		int low = 0;
		int high = arr.length - 1;
		int mid = 0;
		fib();
		while (high > fib[k] - 1)
		{
			k++;
		}
		// 复制数组到f[k]长度
		int[] temp = Arrays.copyOf(arr, fib[k]);
		for (int i = high + 1; i < temp.length; i++)
		{
			temp[i] = arr[high];
		}
		int index = -1;
		while (low <= high)
		{
			mid = low + fib[k - 1] - 1;
			if (key < temp[mid])
			{
				high = mid - 1;
				// 黄金分割点变换到左边
				k--;
			} else if (key > temp[mid])
			{
				low = mid + 1;
				// 黄金分割点变换到右边
				k -= 2;
			} else
			{
				// 找到了,看是不是补全值
				if (mid <= temp.length - 1)
				{
					index = mid;
					return index;
				} else
				{
					index = temp.length - 1;
					return index;
				}
			}

		}
		return index;

	}

}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值