if (mainThread)
{
+
+ int rootComplexity;
+ if (Eval::useNNUE)
+ Eval::NNUE::evaluate(rootPos, true, &rootComplexity);
+ else
+ Eval::evaluate(rootPos, &rootComplexity);
+
+ mainThread->complexity = std::min(1.03 + (rootComplexity - 241) / 1552.0, 1.45);
+
if (mainThread->bestPreviousScore == VALUE_INFINITE)
for (int i = 0; i < 4; ++i)
mainThread->iterValue[i] = VALUE_ZERO;
multiPV = std::min(multiPV, rootMoves.size());
- complexityAverage.set(153, 1);
-
optimism[us] = optimism[~us] = VALUE_ZERO;
int searchAgainCounter = 0;
timeReduction = lastBestMoveDepth + 8 < completedDepth ? 1.57 : 0.65;
double reduction = (1.4 + mainThread->previousTimeReduction) / (2.08 * timeReduction);
double bestMoveInstability = 1 + 1.8 * totBestMoveChanges / Threads.size();
- int complexity = mainThread->complexityAverage.value();
- double complexPosition = std::min(1.03 + (complexity - 241) / 1552.0, 1.45);
- double totalTime = Time.optimum() * fallingEval * reduction * bestMoveInstability * complexPosition;
+ double totalTime = Time.optimum() * fallingEval * reduction * bestMoveInstability * mainThread->complexity;
// Cap used time in case of a single legal move for a better viewer experience in tournaments
// yielding correct scores and sufficiently fast moves.
(ss+2)->cutoffCnt = 0;
ss->doubleExtensions = (ss-1)->doubleExtensions;
Square prevSq = is_ok((ss-1)->currentMove) ? to_sq((ss-1)->currentMove) : SQ_NONE;
-
- // Initialize statScore to zero for the grandchildren of the current position.
- // So statScore is shared between all grandchildren and only the first grandchild
- // starts with statScore = 0. Later grandchildren start with the last calculated
- // statScore of the previous grandchild. This influences the reduction rules in
- // LMR which are based on the statScore of parent position.
- if (!rootNode)
- (ss+2)->statScore = 0;
+ ss->statScore = 0;
// Step 4. Transposition table lookup.
excludedMove = ss->excludedMove;
tte->save(posKey, VALUE_NONE, ss->ttPv, BOUND_NONE, DEPTH_NONE, MOVE_NONE, eval);
}
- thisThread->complexityAverage.update(complexity);
-
// Use static evaluation difference to improve quiet move ordering (~4 Elo)
if (is_ok((ss-1)->currentMove) && !(ss-1)->inCheck && !priorCapture)
{
{
// Futility pruning for captures (~2 Elo)
if ( !givesCheck
- && !PvNode
&& lmrDepth < 6
&& !ss->inCheck
&& ss->staticEval + 182 + 230 * lmrDepth + PieceValue[EG][pos.piece_on(to_sq(move))]
lmrDepth = std::max(lmrDepth, 0);
- Bitboard occupied;
// Prune moves with negative SEE (~4 Elo)
- if (!pos.see_ge(move, occupied, Value(-24 * lmrDepth * lmrDepth - 15 * lmrDepth)))
+ if (!pos.see_ge(move, Value(-24 * lmrDepth * lmrDepth - 15 * lmrDepth)))
continue;
}
}
if (singularQuietLMR)
r--;
- // Decrease reduction if we move a threatened piece (~1 Elo)
- if ( depth > 9
- && (mp.threatenedPieces & from_sq(move)))
- r--;
-
// Increase reduction if next ply has a lot of fail high (~5 Elo)
if ((ss+1)->cutoffCnt > 3)
r++;
prevSq);
int quietCheckEvasions = 0;
- Bitboard occupied;
// Step 5. Loop through all pseudo-legal moves until no moves remain
// or a beta cutoff occurs.
continue;
}
- if (futilityBase <= alpha && !pos.see_ge(move, occupied, VALUE_ZERO + 1))
+ if (futilityBase <= alpha && !pos.see_ge(move, VALUE_ZERO + 1))
{
bestValue = std::max(bestValue, futilityBase);
continue;
continue;
// Do not search moves with bad enough SEE values (~5 Elo)
- if (!pos.see_ge(move, occupied, Value(-110)))
+ if (!pos.see_ge(move, Value(-110)))
continue;
}