二分查找、差值查找、斐波那契查找

二分法查找适用于大的数据,但前提条件是数据必须是有序的,他的原理是先和中间的比较,如果等于就直接返回,如果小于就在前半部分继续使用二分法进行查找,如果大于则在后半部分继续使用二分法进行查找。
代码:

public class Search {
	public static void main(String[] args) {
		// TODO Auto-generated method stub
		int[] arr = new int[]{1,2,3,4,5,6,7,8,9};
		System.out.println(binarySearch(arr, 3));

	}
	public static int binarySearch(int[] arr, int value) {
		int low = 0;
		int high = arr.length-1;
		while(low<=high) {
			int middle = low + ((high - low) >> 1);
//			int middle = (low+high) / 2;
			if(arr[middle]==value) {
				return middle;
			}
			if(arr[middle]>value) {
				high = middle - 1;
			}else {
				low = middle + 1;
			}
		}
		return -1;
	}
}

用递归写二分法:

public class Search {
	public static void main(String[] args) {
		// TODO Auto-generated method stub
		int[] arr = new int[]{1,2,3,4,5,6,7,8,9};
		System.out.println(binarySearchDiGui(arr, 3));

	}
	public static int binarySearchDiGui(int[] arr, int value) {
		int low = 0;
		int high = arr.length-1;
		return search(arr, low, high, value);
	}
	public static int search(int[] arr, int low, int high, int value) {
		if(low>high) {
			return -1;
		}
		int middle = low + (high-low)>>2;
		if(arr[middle]==value) {
			return middle;
		}
		if(arr[middle]>value) {
			return search(arr, low, middle-1, value);
		}else {
			return search(arr, middle+1, high, value);
		}
	}
}

差值法
二分法查然效率很高,但我们为什么要和中间的值进行比较,如果我们和数组1/4或者3/4部分的值进行比较可不可以呢,对于一个要查找的数我们不知道他大概在数组的什么位置的时候我们可以使用二分法进行查找。但如果我们知道要查找的值大概在数组的最前面或最后面的时候使用二分法查找显然是不明智的。比如我们查字典的时候如果是a或者b开头的我们一般会在前面找,如果是y或者z开头的我们一般偏向于往后面找,这个时候如果我们使用二分法从中间开始找显然是不合适的。之前二分法查找的时候我们比较的是中间值,mid=low+1/2*(high-low);但插值查找的时候我们比较的不是中间值,是mid=low+(key-a[low])/(a[high]-a[low])*(high-low),我们来看下插值查找的代码。

public class Search {
	public static void main(String[] args) {
		// TODO Auto-generated method stub
		int[] arr = new int[]{1,2,3,4,5,6,7,8,9};
		System.out.println(binarySearch(arr, 3));

	}
	public static int ChaZhiSearch(int[] arr, int value) {
		int low = 0;
		int high = arr.length-1;
		while(low<=high) {
			if(arr[high]==arr[low]) {
				if(arr[high]==value) {
					return high;
				}else {
					return -1;
				}
			}
			int middle = low + (value-arr[low])/(arr[high]-arr[low]) * (high-low);
			if(arr[middle]==value) {
				return middle;
			}
			if(arr[middle]>value) {
				high = middle - 1;
			}else {
				low = middle + 1;
			}
		}
		return -1;
	}
}

这里将middle的计算方法改变了,可以看成按照比例进行定位。另外,由于分母可能为0,所以上面做了判断。

斐波那契查找法

你可能感兴趣的:(排序和查找)