From 1db969e6200afe4f023469a56aa5edf755d92bbb Mon Sep 17 00:00:00 2001 From: rn5f107s2 Date: Thu, 15 Feb 2024 23:01:02 +0100 Subject: [PATCH] Reduce futility_margin if opponents last move was bad This reduces the futiltiy_margin if our opponents last move was bad by around ~1/3 when not improving and ~1/2.7 when improving, the idea being to retroactively futility prune moves that were played, but turned out to be bad. A bad move is being defined as their staticEval before their move being lower as our staticEval now is. If the depth is 2 and we are improving the opponent worsening flag is not set, in order to not risk having a too low futility_margin, due to the fact that when these conditions are met the futility_margin already drops quite low. Passed STC: https://tests.stockfishchess.org/tests/live_elo/65e3977bf2ef6c733362aae3 LLR: 2.94 (-2.94,2.94) <0.00,2.00> Total: 122432 W: 31884 L: 31436 D: 59112 Ptnml(0-2): 467, 14404, 31035, 14834, 476 Passed LTC: https://tests.stockfishchess.org/tests/live_elo/65e47f40f2ef6c733362b6d2 LLR: 2.94 (-2.94,2.94) <0.50,2.50> Total: 421692 W: 106572 L: 105452 D: 209668 Ptnml(0-2): 216, 47217, 114865, 48327, 221 closes https://github.com/official-stockfish/Stockfish/pull/5092 Bench: 1565939 --- src/search.cpp | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/src/search.cpp b/src/search.cpp index 8ed7841e..f135a090 100644 --- a/src/search.cpp +++ b/src/search.cpp @@ -53,11 +53,13 @@ using namespace Search; namespace { - // Futility margin -Value futility_margin(Depth d, bool noTtCutNode, bool improving) { - Value futilityMult = 117 - 44 * noTtCutNode; - return (futilityMult * d - 3 * futilityMult / 2 * improving); +Value futility_margin(Depth d, bool noTtCutNode, bool improving, bool oppWorsening) { + Value futilityMult = 117 - 44 * noTtCutNode; + Value improvingDeduction = 3 * improving * futilityMult / 2; + Value worseningDeduction = (331 + 45 * improving) * oppWorsening * futilityMult / 1024; + + return futilityMult * d - improvingDeduction - worseningDeduction; } constexpr int futility_move_count(bool improving, Depth depth) { @@ -533,7 +535,7 @@ Value Search::Worker::search( Move ttMove, move, excludedMove, bestMove; Depth extension, newDepth; Value bestValue, value, ttValue, eval, maxValue, probCutBeta; - bool givesCheck, improving, priorCapture; + bool givesCheck, improving, priorCapture, opponenWorsening; bool capture, moveCountPruning, ttCapture; Piece movedPiece; int moveCount, captureCount, quietCount; @@ -742,6 +744,8 @@ Value Search::Worker::search( ? ss->staticEval > (ss - 2)->staticEval : (ss - 4)->staticEval != VALUE_NONE && ss->staticEval > (ss - 4)->staticEval; + opponenWorsening = ss->staticEval + (ss - 1)->staticEval > 2 && (depth != 2 || !improving); + // Step 7. Razoring (~1 Elo) // If eval is really low check with qsearch if it can exceed alpha, if it can't, // return a fail low. @@ -756,7 +760,7 @@ Value Search::Worker::search( // Step 8. Futility pruning: child node (~40 Elo) // The depth condition is important for mate finding. if (!ss->ttPv && depth < 11 - && eval - futility_margin(depth, cutNode && !ss->ttHit, improving) + && eval - futility_margin(depth, cutNode && !ss->ttHit, improving, opponenWorsening) - (ss - 1)->statScore / 314 >= beta && eval >= beta && eval < 30016 // smaller than TB wins