圍棋提子算法
主題詞:圖,數(shù)據(jù)結(jié)構(gòu),遞歸,分支結(jié)構(gòu),堆棧,入口坐標(biāo)恢復(fù),遍歷路徑
最近用c#語言做圍棋打譜軟件,想做一個比較全面的圍棋提子函數(shù)。以前做的是單側(cè)的圍棋提子函數(shù),很簡明,分左上右下四個方向調(diào)用四次圍棋提子函數(shù),就可以解決圍棋提子問題。如今,自我感覺編程水平提高了,就想調(diào)用 一次圍棋提子函數(shù)就解決圍棋提子問題。綜合的圍棋提子函數(shù)主要就是在遞歸算法里加入分支判斷。
圍棋盤是圖結(jié)構(gòu),可以映射成數(shù)組或者線性鏈表。圍棋提子問題可以抽象為對圖的深度優(yōu)先遍歷問題。我采用遞歸調(diào)用進行深度優(yōu)先遍歷,再用分支結(jié)構(gòu)解決圍棋提子判斷。
圍棋提子判斷的主要問題集中在:
1,添加分支標(biāo)記和判斷。因為一顆棋子要進行左上右下四個分支的判斷和遞歸調(diào)用。
2,遞歸調(diào)用時入口坐標(biāo)的保存和恢復(fù)。多層遞歸調(diào)用會出現(xiàn)棋子坐標(biāo)的轉(zhuǎn)移。需要保存和恢復(fù)每次調(diào)用時的入口棋子坐標(biāo)。用堆棧的方法處理入口棋子坐標(biāo)很簡明有效。
當(dāng)然,一個完整無錯的圍棋提子函數(shù),還要解決邊界判斷,禁入點,打劫等問題。一般用窮舉法就可以解決,比如將所有邊界的類型都羅列出來,然后逐一判斷解決就可以了。
將代碼塊封裝為函數(shù),一般要求該函數(shù)的功能盡量單一化,如此也有利于代碼復(fù)用。一個函數(shù)里復(fù)合了多個功能,這個函數(shù)的用途就很有限了。
我把所有四個方向的圍棋提子判斷放在一個函數(shù)里解決,無非是測試一下自己的編碼水平,這并不是好的解決方案。這樣做,編碼的錯誤率高了很多,調(diào)試排錯也很浪費時間。現(xiàn)在還在調(diào)試排錯進行中......無語。不過,如
果成功,對于提高思維的縝密程度,是一次很好的練習(xí)。
周末集中上圍棋課,沒有時間寫代碼。周一上午重新調(diào)試圍棋提子算法,主要是功能和邏輯錯誤,錯誤原因是對分支標(biāo)記的處理有疏漏之處。得到的經(jīng)驗是:標(biāo)志位的賦值,遍歷用的暫時鏈表的更新,最好放在遞歸調(diào)用的前
后及時處理。圍棋提子判斷之后,要將棋盤鏈表初始化。否則,會影響下一次提子判斷。
小結(jié):
1、有四個分支的遞歸函數(shù),if_else嵌套常常達(dá)到5層以上,代碼結(jié)構(gòu)復(fù)雜,邏輯關(guān)系復(fù)雜,編碼時很容易出錯。代碼的調(diào)試和維護也很困難。
2、實用的代碼應(yīng)該是:函數(shù)功能單一,代碼結(jié)構(gòu)簡明,邏輯關(guān)系清晰,易于維護和調(diào)試。
3、編寫成功有分支結(jié)構(gòu)的圍棋提子函數(shù),對自己的復(fù)雜邏輯思維和調(diào)試代碼的耐心是一次很好的鍛煉。
愛華網(wǎng)



