剪枝搜索

剪枝搜索是搜索中常用的一个方法,Binary Search就是一个经典的剪枝搜索例子,在Biniary Search中

int binarySearch(int A[], int low, int high, int key)
{
    int mid;
    while (low <= high)
    {
        mid = (low + high) >> 1;
        if (key < A[mid]) high = mid - 1;
        else if (key > A[mid]) low = mid + 1;
        else return mid;
    }
    return -1;
}

我们可以明显看到,当目标被锁定在一半区域内时,就剪掉另一半,并对所在的一半进行搜索。而此时问题化简成为一个只有一半数据规模的子问题,递归这一过程,最终就可以在常数时间解决搜索问题。

另一个剪枝搜索的经典实例是寻找一组数中第K小的数的值,直观的想法是进行一次排序,而后求解。但即使是使用最合适于此问题的堆排序,也要用到O(NlogN)的时间,实际上,利用剪枝搜索有一种O(n)时间的算法如下:

选取数组中一个数P,遍历数组,将所有数据与P比较,小于P的数字置于集合S1,等于P的数字置于集合S2,大于P的数字置于集合S3

若S1.size>K,舍弃S2,S3,以S1为基础重复此问题。

否则 若S1.size+S2.size>K,则P为第K个数的值。

否则 舍弃S1,S2,以S3为基础重复此问题。

代码以后补

 

对于剪枝搜索问题的复杂度,我们可以看到

T(n)=T((1-f)*n)+O(n^k),最终的复杂度取决于k即为O(n^k),当n趋于无穷时,解决问题的实质复杂度和解决子问题的复杂度趋于一致。

(例如,对于Binary Search,T(n)=T(n/2)+C

设n=2^k,则有T(2^k)=T(2^(k-1))+C=(T(2^(k-2))+C)+C=T(1)+k*C

即T(n)=log(n)*C+T(1),所以binary search是一个O(log(n))的算法,在n趋于无穷时log(n)趋于常数代价)

 

posted @ 2016-07-10 15:17  CieloSun  阅读(658)  评论(0编辑  收藏  举报