鍵只用了每個角色的首字母
三次重複需要一種方法來判斷「這是同一個局面」。Mistboard 把每個局面轉成一個字串,並統計每個字串出現了幾次。
function repetitionKey(position):
parts = []
for sq, p in position.pieces (sorted by sq):
# red chariot on a1: "a1" + "r" + "c"
parts.append(sq + p.color[0] + p.role[0])
return position.turn + "|" + join(parts, ",")
after every move:
seen[repetitionKey(position)] += 1
if it reaches 3: draw (or a perpetual-check loss)role[0] 是角色名的首字母,而象棋的七種角色裡有兩種以 c 開頭。a1 上的紅車和 b3 上的紅炮分別寫成 a1rc 和 b3rc。兩者互換後,寫出來仍然是 a1rc 和 b3rc。
十四步合法著法,判出一盤和棋
紅方用五步完成互換,同時黑方把一個車走出去再走回來;然後雙方各把一個馬跳出去再跳回來:
| 走完 | 舊計數 | 實際計數 |
|---|---|---|
| 開局 | 1 | 開局局面:1 |
| 互換,每方 5 步 | 2 | 互換局面:1 |
| 馬跳出再跳回 | 3,判和 | 互換局面:2 |
十四步合法著法,網站就判了和棋。沒有棋手回報過這個問題;它是在給揭棋加上重複局面規則時,閱讀這段程式碼發現的。
修復:把角色名完整寫出
# red chariot on a1: "a1:r.chariot"
parts.append(sq + ":" + p.color[0] + "." + p.role)一個測試會走完這十四步,並檢查對局仍在繼續。迷霧國際象棋(王 king 和馬 knight 都是 k)和鴨子象棋裡也有同樣的簡寫;兩者都已修復。
對網站意味著什麼
已結束的對局:沒有一盤改變。用修正後的鍵重放,全部 29 盤象棋重複局面和棋、2 盤長將判負、2 盤鴨子象棋和棋和 19 盤迷霧國際象棋和棋,結果都一樣。
新對局:象棋、迷霧象棋、迷霧國際象棋和鴨子象棋,只有在同一局面真正出現三次時,才會因重複局面結束。
謎題:謎題挖掘器的查重會同時識別新舊兩種寫法,所以已發布的謎題不會被當成新題再出現。
用縮寫拼成的鍵需要一項檢查,而這項檢查從任何單個縮寫上都看不出來:沒有兩個名字縮寫成同一個東西。手寫的字母表在有人為車選定 r 的那一刻,就做了這項檢查。role[0] 從來沒有做過。