Skip to content
Permalink
Browse files

Add KNNvKP Endgame Heuristic

This is a somewhat different patch. It fixes blindspots for
 two knights vs pawn endgame.

With local testing starting from random KNNvKP positions where the
pawn has not advanced beyond the 4th rank (thanks @protonspring !)
at 15+0.15 (4 cores), this went +105=868-27 against master. All except
two losses were won in reverse.

The heuristic is simple but effective - the strategy in these endgames
is to push the opposing king to the corner, then move the knight that's
blocking the pawn in for the checkmate while the pawn is free to move
and prevents stalemate. This patch gives SF the little boost it needs
to search the relevant king-cornering mating lines.

See the discussion in pull request 1939 for some more good results for
this test in independant tests:
official-stockfish#1939

Bench: 3310239
  • Loading branch information...
Kurtbusch authored and snicolet committed Jan 4, 2019
1 parent e51244c commit badb2aca44d6507f35dafc8b5c3921a6649a40f8
Showing with 18 additions and 1 deletion.
  1. +15 −0 src/endgame.cpp
  2. +2 −0 src/endgame.h
  3. +1 −1 src/search.cpp
@@ -286,6 +286,21 @@ Value Endgame<KQKR>::operator()(const Position& pos) const {
}


/// KNN vs KP. Simply push the opposing king to the corner.
template<>
Value Endgame<KNNKP>::operator()(const Position& pos) const {

assert(verify_material(pos, strongSide, 2 * KnightValueMg, 0));
assert(verify_material(pos, weakSide, VALUE_ZERO, 1));

Value result = 2 * KnightValueEg
- PawnValueEg
+ PushToEdges[pos.square<KING>(weakSide)];

return strongSide == pos.side_to_move() ? result : -result;
}


/// Some cases of trivial draws
template<> Value Endgame<KNNK>::operator()(const Position&) const { return VALUE_DRAW; }

@@ -37,6 +37,7 @@ enum EndgameCode {

EVALUATION_FUNCTIONS,
KNNK, // KNN vs K
KNNKP, // KNN vs KP
KXK, // Generic "mate lone king" eval
KBNK, // KBN vs K
KPK, // KP vs K
@@ -125,6 +126,7 @@ class Endgames {
add<KRKN>("KRKN");
add<KQKP>("KQKP");
add<KQKR>("KQKR");
add<KNNKP>("KNNKP");

add<KNPK>("KNPK");
add<KNPKB>("KNPKB");
@@ -830,7 +830,7 @@ namespace {
int probCutCount = 0;

while ( (move = mp.next_move()) != MOVE_NONE
&& probCutCount < 2 + 2 * cutNode)
&& probCutCount < 2 + 2 * cutNode)
if (move != excludedMove && pos.legal(move))
{
probCutCount++;

0 comments on commit badb2ac

Please sign in to comment.
You can’t perform that action at this time.