一步步學資料結構與演算法 15 二分查詢 上

2021-09-25 16:02:52 字數 1454 閱讀 3565

二分查詢針對的是乙個有序的資料集合,每次通過跟區間中間的元素對比,將待查詢的區間縮小為之前的一半,直到找到要查詢的元素,或者區間縮小為0。

1.時間複雜度

假設資料大小是n,每次查詢後資料都會縮小為原來的一半,最壞的情況下,直到查詢區間被縮小為空,才停止。所以,每次查詢的資料大小是:n,n/2,n/4,…,n/(2k),…,這是乙個等比數列。當n/(2k)=1時,k的值就是總共縮小的次數,也是查詢的總次數。而每次縮小操作只涉及兩個資料的大小比較,所以,經過k次區間縮小操作,時間複雜度就是o(k)。通過n/(2^k)=1,可求得k=log2n,所以時間複雜度是o(logn)。

2.認識o(logn)

①這是一種極其高效的時間複雜度,有時甚至比o(1)的演算法還要高效。為什麼?

②因為logn是乙個非常「恐怖「的數量級,即便n非常大,對應的logn也很小。比如n等於2的32次方,也就是42億,而logn才32。

③由此可見,o(logn)有時就是比o(1000),o(10000)快很多。

1.迴圈實現

**實現:

public int binarysearch1(int a, int val)

return -1;

}

注意事項:

①迴圈退出條件是:start<=end,而不是start> 1),因為相比除法運算來說,計算機處理位運算要快得多。

③start和end的更新:start = mid - 1,end = mid + 1,若直接寫成start = mid,end=mid,就可能會發生死迴圈。

2.遞迴實現

public int binarysearch(int a, int val)

private int bsear(int a, int val, int start, int end)

1.二分查詢依賴的是順序表結構,即陣列。

2.二分查詢針對的是有序資料,因此只能用在插入、刪除操作不頻繁,一次排序多次查詢的場景中。

3.資料量太小不適合二分查詢,與直接遍歷相比效率提公升不明顯。但有乙個例外,就是資料之間的比較操作非常費時,比如陣列中儲存的都是長度超過300的字串,那這是還是儘量減少比較操作使用二分查詢吧。

4.資料量太大也不是適合用二分查詢,因為陣列需要連續的空間,若資料量太大,往往找不到儲存如此大規模資料的連續記憶體空間。

1.如何在1000萬個整數中快速查詢某個整數?

①1000萬個整數占用儲存空間為40mb,占用空間不大,所以可以全部載入到記憶體中進行處理;

②用乙個1000萬個元素的陣列儲存,然後使用快排進行公升序排序,時間複雜度為o(nlogn)

③在有序陣列中使用二分查詢演算法進行查詢,時間複雜度為o(logn)

2.如何程式設計實現「求乙個數的平方根」?要求精確到小數點後6位?

一步步學資料結構與演算法 10 遞迴

1.遞迴是一種非常高效 簡潔的編碼技巧,一種應用非常廣泛的演算法,比如dfs深度優先搜尋 前中後序二叉樹遍歷等都是使用遞迴。2.方法或函式呼叫自身的方式稱為遞迴呼叫,呼叫稱為遞,返回稱為歸。3.基本上,所有的遞迴問題都可以用遞推公式來表示,比如 f n f n 1 1 f n f n 1 f n 2...

一步步學資料結構與演算法 20 雜湊演算法 上

帶著問題來學習 1.如何防止資料庫中的使用者資訊被脫庫?2.你會如何儲存使用者密碼這麼重要的資料嗎?僅僅 md5 加密一下儲存就夠了嗎?3.在實際開發中,我們應該如何用雜湊演算法解決問題?1.定義 將任意長度的二進位制值串對映成固定長度的二進位制值串,這個對映的規則就是雜湊演算法,而通過原始資料對映...

一步步學資料結構與演算法 09 佇列

1.先進者先出,這就是典型的 佇列 結構。2.支援兩個操作 入隊enqueue 放乙個資料到隊尾 出隊dequeue 從隊頭取乙個元素。3.所以,和棧一樣,佇列也是一種操作受限的線性表。1.佇列api public inte ce queue2.陣列實現 順序佇列 public class arra...