揭棋引擎審查意見的實測
簡而言之
- 一份針對 Mistboard 揭棋機器人背後引擎的外部審查,發現了一個真實的評估函式缺陷:其中一方的暗子從未被計入。
- 修復後對原版引擎得分 0.475;圍繞修復重新調校相關的 43 項參數,得分 0.507;替換審查所批評的身分平均,得分 0.370。
- 機器人維持原樣。手工調校的評估函式會吸收自身的缺陷,200 局的門檻看不出 +10 Elo,而任何從這個引擎衍生出來的東西都贏不了它。
iwestlin/jieqi-ai 收錄了 Pikafish 的 jieqi_old 分支,也就是 Mistboard 上揭棋機器人背後的引擎,並附上一份原始碼審查 ai分析.md。它的五項發現中,兩項是已知限制,一項誤讀了規則,另有兩項值得打一場對抗賽:評估函式中的一個真實缺陷,以及「在搜尋中對隱藏身分取平均並不可靠」的說法。
jieqi_old 是 alpha-beta 搜尋加上手寫的評估函式,沒有神經網路。它先前已經撐過了十個從它自身評估值蒸餾出來的神經網路(最好的得分 0.43),也撐過了在一盤被人類贏下的棋上給它十五倍的搜尋時間(著法完全相同)。以下還有三項測試,做法都一樣:改動後的引擎對原版引擎,輪流執紅執黑,每著用時相同,由裁判程式發放身分,兩個引擎都看不到暗子。
缺陷:一方的暗子從未被計入
Evaluation::initialize<Us>() 會為白方和黑方各執行一次。每次呼叫都會清空整個 DarkPieces 陣列,只重新填入自己一方,所以等到威脅項讀取它時,白方的暗子已經不見了:
memset(DarkPieces, 0, sizeof DarkPieces); // both colours, every call
for (PieceType i = ROOK; i <= BISHOP; ++i) {
Bitboard b = pos.pieces(Us, i); // only Us is refilled
...
引擎的 eval 追蹤輸出證實了這一點:黑卒攻擊紅方暗子時,修復前 Threats 一列雙方完全相同,修復後則與紅攻黑的情形互為鏡像。紅方攻擊暗子會得分,黑方從來不會。
測試一:修復它
黑方一直少了一項紅方擁有的評估項,所以把它補給黑方應該會有幫助。
每著 500 毫秒,200 局:91-101-8,得分 0.475 ± 0.068。 執紅 0.525,執黑 0.425。
新拿到這項加分的一方反而下得更差,所以這些權重不只是算錯了,本身也是錯的。原始碼裡那些奇怪的數值(S(-11, 2)、S(39, -26))說明它們曾經靠實戰調校過一次,而當時缺陷就在裡面。公式正確、權重照舊,就是另一個沒調過參的引擎。
測試二:圍繞修復重新調參
如果這些權重是為有缺陷的公式調出來的,那麼為修復後的公式重新調參,應該能找回測試一損失的部分,並發現缺陷所掩蓋的東西。
缺陷涉及的 43 項參數,透過 Pikafish 的 TUNE 功能公開為 UCI 選項,再在筆電上跑 fishtest 式的 SPSA:10,000 對對局,每著 100 毫秒,六小時。43 項中有 41 項發生變動,變動最大的是暗子著法分數的上限(2862 到 2745)。調參版對原版,每著 500 毫秒,200 局:96-93-11,得分 0.507 ± 0.067。
仍在持平的誤差範圍內,只是這次落在另一邊。只修復得 0.475,修復加調參得 0.507,說明這些參數怎麼調都沒多少棋力,而不是調得不夠。在租用的 CPU 上跑 50,000 對只要幾美元,但這兩個結果並不支持這麼做。
測試三:替換身分平均
搜尋走動暗子時,會對該方子池中剩下的每種身分各分支一次,再把結果合併:一個有截斷的加權平均,當平均值遠高於最壞情況時就退回最壞情況。審查說得對,這不是資訊集搜尋;我自己也有懷疑它的理由:7 月時,這個公式選了一步真實期望勝率為 64% 的暗子著法,而不是一步勝率 97% 的穩妥著法。
如果這個公式替賭博定價有誤,那麼正確定價應該能選出更好的著法:當引擎的首選是走動自己的暗子時,取它的前四個候選,對每個賭博的每種身分分別搜尋,平均勝率,走平均值最高的一步。
以包裝程式實作。根節點用時 400 毫秒、每種身分 100 毫秒,100 局:30-56-14,得分 0.370,用時是原版引擎的 2.2 倍。每種身分都給足 400 毫秒,50 局:17-26-7,得分 0.410,用時是七倍。
它在每種預算下都輸,所以是方法錯了,而不是資源不夠。各自獨立的搜尋之間的分歧,比同一棵樹內部的分歧更大;審查所反對的最壞情況退回,其實在發揮作用。7 月那個局面確實是個錯誤;這個療法製造的錯誤比它消除的還多。
手工調校的評估函式為何難以逐項修補
評估函式是當作一個整體調校的。每個權重都是在與其他所有權重(包括那個缺陷)的對弈中定下來的,所以修復一項會退步,重調一組也只能找回修復所損失的部分。要改進它,就得把全部參數重調一遍,也就是原作者當初做過一次的工作。
門檻太粗。200 局的對抗賽在 95% 信賴水準下誤差約 ± 0.07,大約 ± 25 Elo:價值 +10 的改動看不出來,價值 +30 的也跟擲硬幣差不多。更細的門檻需要 1,000 局,在筆電上每個候選要跑一天。
沒有外部標尺。暗棋有開源引擎可以對照,揭棋沒有,所以任何從原版引擎蒸餾或對著它調出來的東西,按構造就會落在原版引擎的水準。老師所缺的訊號是有深度的自我對弈,而這正是替 jieqi 分支訓練神經網路所需要的。
會有什麼改變
已上線的機器人不做任何改動。改動它的固定版本意味著新的網頁瀏覽器版本、新的引擎 ID,以及重新計算所有快取的揭棋復盤,而這裡沒有任何結果值得這樣做。這個缺陷修復要等到它所在的評估函式被替換時再說。
固定的版本現在附帶 Linux 執行檔和網頁瀏覽器版本,上面每個數字背後的訓練器、特徵集、裁判程式、對抗賽框架和調參器都已公開。一個對已上線機器人 200 局得分 0.55 的神經網路,就會成為新的機器人。