二分搜尋及其變形討論

2021-07-01 20:05:09 字數 1396 閱讀 3193

最近刷leetcode的時候遇到了不少二分查詢的題,二分查詢是非常高效的查詢策略,但是有乙個前提就是陣列必須是有序的。

1. 對於標準的二分搜尋,針對的是沒有重複元素的有序陣列,每個元素只出現一次。標準的二分搜尋的**很簡潔,對於程式設計師來講最好會背

int std_binary_search(int v, int n, int target)

//l is the position in which target will be inserted

return l;

}

需要注意的是如果查詢的目標不在陣列中所返回的值,一般情況下返回-1比較好,但是如果要求返回target插入到陣列中的位置,那麼可以返回l,但是需要注意的就是返回之後一定要驗證v[l]是不是taget,因為無法判斷返回的這個位置是target還是待插入的位置。

2. 如果陣列中有重複的元素,而且二分查詢的時候要求返回重複元素的起始位置和結束位置,那麼上面的**就不管用了。主要解決思路是進行兩次二分搜尋,第一次找到最左邊的target,第二次找到最右邊的target。程式的**基本不變,但是需要修改判斷條件,**如下,可以對比上面的程式注意一下修改的判斷條件。

//if the array has duplicate elements

vectordup_binary_search(int v, int n, int target)

left_p = l;

//find the most right position

l = 0;

r = n - 1;

while(l <= r)

right_p = r;

vectorresult;

if(v[left_p] == v[right_p])

else

return result;

}

3. 第三種情況就是陣列旋轉過,即乙個有序的陣列平移了若干個元素,比如[6,7,0,1,2,3,4,5]這個陣列,如果在這個陣列中找到目標元素,使用二分查詢也是可以的。首先我們可以觀察到一點,就是如果從陣列的中間的元素分開,那麼一定有一半是有序陣列,而另外一半是乙個旋轉過的有序陣列,這樣就可以進行判斷,如果target在有序的部分,直接使用標準的二分策略就可以,如果落在另一半,那麼重複上面的過程就可以了。

//if the array has been translation like [5,6,7,1,2,3,4]

int trans_binary_search(int v, int n ,int target)

//if the right part is in right order

else

}return -1;

}

二分查詢及其變形

一 把乙個陣列最開始的若干個元素搬到陣列的末尾,我們稱之為陣列的旋轉。輸入乙個非遞減排序的陣列的乙個旋轉,輸出旋轉陣列的最小元素。例如陣列為的乙個旋轉,該陣列的最小值為1。note 給出的所有元素都大於0,若陣列大小為0,請返回0。方法一 o n public int minnumberinrota...

二分查詢及其變形

最基本的二分查詢模版 在有序陣列a中查詢key,如果找到,返回位置索引,否則,返回 1 int binarysearch int a,int n,int key else if a mid key else return 1 變種1 如果a有多個key元素,返回最大的,否則,返回 1 int bin...

二分搜尋及其擴充套件

二分搜尋需要注意開閉區間的問題,限制條件和邊界要保持配對 low high low mid 1 high mid 1。二分搜尋的模板如下 cpp view plain copy 二分搜尋 intbinarysearch int num,intkey,intlow,inthigh return low...