算法:當數據量很大適宜采用該方法。采用二分法查找時,數據需是排好序的。 基本思想:假設數據是按升序排序的,對於給定值x,從序列的中間位置開始比較,如果當前位置值等於x,則查找成功;若x小於當前位置值,則在數列的前半段 中查找;若x大於當前位置值則在數列的后半段中繼續查找,直到找到為止。
二分法查找在針對大量有序排列的情況下發揮出很優越的效率,這里以最具規律性的數組為例,代碼如下:
示例代碼:
/* binarysearch2.c --- * * Filename: binarysearch2.c * Description: 用循環方式和遞歸兩種方式 實現二分法查找過程 * Author: magc * Maintainer: * Created: 三 7月 25 23:26:52 2012 (+0800) * Version: * Last-Updated: 四 7月 26 00:22:37 2012 (+0800) * By: magc * Update #: 74 * URL: * Keywords: 遞歸 二分法查找 * Compatibility: * */ /* Commentary: * * * */ /* Change Log: * 添加循環方式和遞歸方式 * */ /* Code: */ #include <assert.h> #include <ctype.h> #include <errno.h> #include <limits.h> #include <string.h> #include <stdarg.h> #include <stdlib.h> #include <stdio.h> int binarysearch(int arr[],int len,int key); int binarysearch2(int array[],int key,int low,int high); int main(int argc, char * argv[]) { int array[] = {3,5,6,7,11,22,44,47 }; int i; printf("請參照下列數組,輸入你要查找的目標:\n {"); int len = sizeof(array)/sizeof(int); for (i = 0; i < len; i++) { printf("%d,",array[i]); } printf("}:\n"); int dest; scanf("%d",&dest); int res = binarysearch(array,len,dest); printf("1. res = %d\n",res); int res2 = binarysearch2(array,dest,0,len - 1); printf("2. res = %d\n",res2); } /************************************************************************** 函數名稱:用循環實現二分法查找過程, 功能描述: 輸入參數: 返 回:返回目標值在數組中的下標 **************************************************************************/ int binarysearch(int arr[],int len,int key) { int high,low; high = len - 1;//假設數組是從小到大排列的 low = 0; int midle = len/2; while(high >= low) { midle = (high + low)/2; if(arr[midle] == key) return midle; if(arr[midle] > key) high = midle - 1; //前提是假設數組是從小到大排序,否則不確定是該加1還是減1 else if(arr[midle] < key ) low = midle + 1; } return (-1); } /************************************************************************** 函數名稱:用遞歸實現二分法查找 功能描述: 輸入參數: 返 回: **************************************************************************/ int binarysearch2(int array[],int key,int low,int high) { if (low >= high) return (-1); int midle = (low + high)/2; if(array[midle] == key) return midle; if(midle == high || midle == low) //此時,只剩下了下標為high和low的兩個數,確定另一個數不是key后,就確定查找完畢,並且未找到目標值 { if(array[high] == key) return high; else if(array[low] == key) return low; else return (-1); } else if(array[midle] > key) return binarysearch2(array,key,low,midle); //由於不確定排序方向,所以此處只能用midle值,而不能加1或減1 else if(array[midle] < key) //當中間值小於目標值時,在high的一側繼續查找,low變到midle位置上 return binarysearch2(array,key,midle,high); } /* binarysearch2.c ends here */
在GCC下編譯運行結果如下:
注:
1)在第一個方法中,
要體會到二分法查找的思路,設置high和low參數的好處是,不論數組是從大到小還是從小到大排列,此函數皆適用。
注意把握此例中high和low的變更過程,特別是邊界,當high和low相鄰時,取到的midle值總是二者之一,若繼續查找,便進入死循環狀態,此時確定沒有目標值,退出查找
3)理解遞歸的思路,凡可以遞歸的問題,一般用循環也能實現(反之不然),如binarysearch2方法。
在整理思路時,要准確把握變與不變因素,進而實現