麻將胡牌的演算法
一個人會不會打麻將有一項基本的判斷方法,「能夠判斷是否胡牌」。在實戰中,判斷的速度越快越好,如此才能在麻將桌上取捨牌的時候,很快的知道打哪張牌聽的牌比較好,也不會因為停下來比畫思考,被看穿手裡擁有的牌型。
要知道聽什麼牌,最快的方式是背起來。常打麻將的人,腦中自然背了不少牌型,常見牌型瞬間就能判斷,除非拿了許多同花色的牌才會造成困擾。
電腦程式如何判斷聽牌?
打麻將要判斷聽牌,得先知道胡牌的牌型,如同要準備晚餐的食材之前,得先知道晚餐想吃什麼。
一般都是刪除「一刻(3張相同牌)」或「一順(3張連續牌)」,也就是所謂的「搭子」,再利用「遞迴」程序處理。這樣做的效率並不太優,雖然判斷一副牌還是瞬間完成,但若要判斷十萬副牌局,效率好壞造成的影響非常之大。
麻將定理1
在麻將玩法中,一副牌P,若把一個對子(俗稱眼睛)拿掉後,假設此時數字最小的牌是x。
若x的張數是3張以上,則拿掉3張x(一刻)後,剩下牌為Q。
否則拿掉x, x+1, x+2(一順)之後,剩下的牌為Q。(若無法拿,則P沒胡)
則「P胡」若且唯若「Q胡」。
舉例說明:
例1:判斷P = 33345678是否胡牌?
P中唯一能當眼睛的地方,就是3,因此把33一對眼睛拿掉,變成Q=345678,Q是胡牌型,所以P也是。
例2:判斷P = 55666777889是否胡牌?
其中55、66、77、88都可以當眼睛,每種情況都試一次。
若55當眼,剩下666777889;最小的6有三張,直接拿掉666,剩777889,再拿777,得889,所以沒胡。
若66當眼,剩下556777889;最小的是兩張5,但沒有辦法拿掉兩個567了,所以沒胡。
若77當眼,剩下556667889;最小的是兩張5,但沒有辦法拿掉兩個567了,所以沒胡。
各種能拿掉眼睛的方式都試過,都無法胡,所以P不是胡牌型。
這樣做的好處,是只要拿掉一副牌的眼睛後,就可以一路由最小的牌取到最大的牌,依序檢驗,「線性時間」即可判斷是否胡牌,避免來來去去的反覆嘗試,省下非常多的計算時間。
已經學會胡牌型之後,判斷聽牌就簡單了。
只要試著加入任何一張牌,再嘗試拿掉各種可能的眼睛,利用定理1判斷是否可以胡牌,即可得知聽哪些牌,僅需要O(n3)的時間。
例3:判斷3456667888聽什麼牌?
加入1,剩13開頭,沒胡
加入2
拿掉66,剩234567888,胡!
拿掉88,剩234566678,沒胡
加入3
拿掉33,剩456667888,沒胡
拿掉66或88,剩334開頭,沒胡
加入4
拿掉44,剩35開頭,沒胡
拿掉66或88,剩3445開頭,沒胡
加入5,略,胡
加入6,略,胡
加入7,略,胡
加入8,略,胡
加入9,略,胡
上述方法雖然是電腦的麻將判斷方式,但其實人腦判斷,也是相同道理,先把可能的眼睛拿出來,然後最小牌能拿走一刻即拿走一刻,否則試著拿走一順,由於人腦很強大,會自動省略一些無關緊要的判斷步驟,因此執行速度並不會太慢。