@@ -635,6 +635,8 @@ def _probe_tablebase(self, moves: Iterable[chess.Move], tb_type: TablebaseType)
635635 best_wdl = - 2
636636 best_metric = 1_000_000
637637 best_real_distance = 0
638+ best_opponent_draw_ratio = 1.0
639+
638640 board_copy = self .board .copy (stack = False )
639641
640642 if tb_type == TablebaseType .GAVIOTA :
@@ -662,21 +664,46 @@ def _probe_tablebase(self, moves: Iterable[chess.Move], tb_type: TablebaseType)
662664 elif wdl > 0 :
663665 metric -= 10_000
664666
667+ opponent_draw_ratio = 1.0
668+ if best_wdl <= 0 and wdl == 0 :
669+ opponent_moves = list (board_copy .legal_moves )
670+ if len (opponent_moves ) > 0 :
671+ opponent_draw_moves = 0
672+ for opponent_move in opponent_moves :
673+ board_copy .push (opponent_move )
674+
675+ opponent_distance = - probe_distance (board_copy )
676+ opponent_wdl = self ._value_to_wdl (opponent_distance , board_copy .halfmove_clock )
677+
678+ if opponent_wdl == 0 :
679+ opponent_draw_moves += 1
680+
681+ board_copy .pop ()
682+
683+ opponent_draw_ratio = opponent_draw_moves / len (opponent_moves )
684+
665685 if best_move :
666686 if wdl > best_wdl :
667687 best_move = move
668688 best_wdl = wdl
669689 best_metric = metric
670690 best_real_distance = real_distance
671- elif wdl == best_wdl and metric < best_metric :
672- best_move = move
673- best_metric = metric
674- best_real_distance = real_distance
691+ best_opponent_draw_ratio = opponent_draw_ratio
692+ elif wdl == best_wdl :
693+ if wdl == 0 :
694+ if opponent_draw_ratio < best_opponent_draw_ratio :
695+ best_move = move
696+ best_opponent_draw_ratio = opponent_draw_ratio
697+ elif metric < best_metric :
698+ best_move = move
699+ best_metric = metric
700+ best_real_distance = real_distance
675701 else :
676702 best_move = move
677703 best_wdl = wdl
678704 best_metric = metric
679705 best_real_distance = real_distance
706+ best_opponent_draw_ratio = opponent_draw_ratio
680707
681708 board_copy .pop ()
682709
0 commit comments