首先感謝朋友們對第一篇文章的鼎力支援,感動中.......

今天說的是選擇排序,包括“直接選擇排序”和“堆排序”。
話說上次“冒泡排序”被快排虐了,而且“快排”赢得了内庫的重用,衆兄弟自然眼紅,非要找快排一比高下。
這不今天就來了兩兄弟找快排算賬。
1.直接選擇排序:
先上圖:
說實話,直接選擇排序最類似于人的本能思想,比如把大小不一的玩具讓三歲小毛孩對大小排個序,
那小孩首先會在這麼多玩具中找到最小的放在第一位,然後找到次小的放在第二位,以此類推。。。。。。
,小孩子多聰明啊,這麼小就知道了直接選擇排序。羨慕中........
對的,小孩子給我們上了一課,
第一步: 我們拿80作為參照物(base),在80後面找到一個最小數20,然後将80跟20交換。
第二步: 第一位數已經是最小數字了,然後我們推進一步在30後面找一位最小數,發現自己最小,不用交換。
第三步:........
最後我們排序完畢。大功告成。
既然是來挑戰的,那就5局3勝制。
比賽結果公布:
堆排序:
要知道堆排序,首先要了解一下二叉樹的模型。
下圖就是一顆二叉樹,具體的情況我後續會分享的。
那麼堆排序中有兩種情況(看上圖了解):
大根堆: 就是說父節點要比左右孩子都要大。
小根堆: 就是說父節點要比左右孩子都要小。
那麼要實作堆排序,必須要做兩件事情:
第一:建構大根堆。
首先上圖:
首先這是一個無序的堆,那麼我們怎樣才能建構大根堆呢?
第一步: 首先我們發現,這個堆中有2個父節點(2,,3);
第二步: 比較2這個父節點的兩個孩子(4,5),發現5大。
第三步: 然後将較大的右孩子(5)跟父節點(2)進行交換,至此3的左孩子堆建構完畢,
如圖:
第四步: 比較第二個父節點(3)下面的左右孩子(5,1),發現左孩子5大。
第五步: 然後父節點(3)與左孩子(5)進行交換,注意,交換後,堆可能會遭到破壞,
必須按照以上的步驟一,步驟二,步驟三進行重新構造堆。
最後構造的堆如下:
第二:輸出大根堆。
至此,我們把大根堆構造出來了,那怎麼輸出呢?我們做大根堆的目的就是要找出最大值,
那麼我們将堆頂(5)與堆尾(2)進行交換,然後将(5)剔除根堆,由于堆頂現在是(2),
是以破壞了根堆,必須重新構造,構造完之後又會出現最大值,再次交換和剔除,最後也就是俺們
要的效果了,
發現自己兄弟被别人狂毆,
,堆排序再也坐不住了,決定要和快排幹一場。
同樣,快排也不甘示弱,誰怕誰?
結果公布:
堆排序此時心裡很尴尬,雙雙被ko,心裡想,一定要撈回面子,一定要赢,
于是堆排序提出了求“前k大問題”。(就是在海量資料中找出前幾大的資料),
快排一口答應,小意思,沒問題。
雙方商定,在2w随機數中找出前10大的數:
求前k大的輸出結果:
最後堆排序趕緊拉着直接選擇排序一路小跑了,因為求前k大問題已經不是他原本來的目的。
ps: 直接選擇排序的時間複雜度為:o(n^2)
堆排序的時間複雜度:o(nlogn)