你現在正在玩大老二。莊家把牌都發完了,你拿起手上的牌,用目光掃射了一遍,準備擬定戰略。運氣好一點,可以馬上把牌分成順子、葫蘆、鐵支等等,但若運氣差一點,只好先把牌由小到大排序,隨機應變。想一想,你會怎麼排?
在各種排序法中,選擇排序是最為直覺的一個方法。從手中的牌組,找出最小的那一張,放到最左邊;接著,撇開最左邊那張牌不看,一樣找出最小的,放在左邊數來第二張。以此類推,重複在未排序的牌中選擇最小的,由左至右排下去,就可以獲得次序由小到大的牌組。
問題來了,該如何找到「最小的」那張牌呢?
你一定覺得,這還用問嗎?掃射一遍就可以找到了。那我們換一個情境。全班總共有三、四十張考卷,請你找出最低分的那一張。你會怎麼做?
如果還沒想到,有請東太平洋漁場時價分析師兼操盤手暨洋流講師:海龍王彼得來給點提示!影片請看到0分40秒:
Learn More →
彼得陸續說了一連串數字,請問,最便宜的海產是什麼?你是怎麼知道的?
沒意外的話,你不可能記下所有數字,而是一個、一個數字仔細聆聽,腦中只記一個數字:最小的那一個。選擇排序法的程式也是這樣的,他需要一個、一個數字去檢查,用一個變數min
,記載每一回合的最小值。來看看動畫說明:
在第一回合的開始,先設min
為最左邊的數字,一路往右找,若遇到更小的數字,他就是新的min
。所有數字都檢查完後,接下來的操作跟我們想的不太一樣,並不是直接把最小值抽出來放到最左邊,而是將他跟最左邊的數字交換位置(swap)。為什麼呢?這跟數字儲存的方式有關。
我們知道,一串數字在程式中,通常會以陣列(array) 的形式儲存。在固定陣列空間(此例是a[6],只能容納6個數字)的前提下,若要把一個數字放到最左邊,好幾個數字都要往右移動,徒增時間成本。將最小值跟最左邊的數字換位置,只有一次操作,就能確保陣列左邊是排序好的狀態。以此類推,你會發現每結束一回合,已排序好(sorted)的數字就多了一個,直到所有數字都排序完成。
BTW,有沒有同學注意到,怎麼數字交換完成,min
還指著同一個地方呢?這是動畫的小bug。因為,在實作環節,我們會用min
來記載最小值所在的位置,而非最小值本身。白話文的意思就是:最小值是第幾個數字。min
成為一個索引值,可以用它取得陣列中的數字,進而交換位置。
如果看懂上面的說明,那麼恭喜你,可以進入程式實作的環節了!
(待改:最大改最小、右邊那一坨缺的流程)
(待)