// Futility and reductions lookup tables, initialized at startup
int FutilityMoveCounts[2][16]; // [improving][depth]
- int Reductions[2][2][64][64]; // [pv][improving][depth][moveNumber]
+ int Reductions[2][64][64]; // [improving][depth][moveNumber]
template <bool PvNode> Depth reduction(bool i, Depth d, int mn) {
- return Reductions[PvNode][i][std::min(d / ONE_PLY, 63)][std::min(mn, 63)] * ONE_PLY;
+ return (Reductions[i][std::min(d / ONE_PLY, 63)][std::min(mn, 63)] - PvNode) * ONE_PLY;
}
// History and stats update bonus, based on depth
{
double r = log(d) * log(mc) / 1.95;
- Reductions[NonPV][imp][d][mc] = int(std::round(r));
- Reductions[PV][imp][d][mc] = std::max(Reductions[NonPV][imp][d][mc] - 1, 0);
+ Reductions[imp][d][mc] = std::round(r);
// Increase reduction for non-PV nodes when eval is not improving
if (!imp && r > 1.0)
- Reductions[NonPV][imp][d][mc]++;
+ Reductions[imp][d][mc]++;
}
for (int d = 0; d < 16; ++d)
int probCutCount = 0;
while ( (move = mp.next_move()) != MOVE_NONE
- && probCutCount < 3)
+ && probCutCount < 2 + 2 * cutNode)
if (move != excludedMove && pos.legal(move))
{
probCutCount++;
movedPiece = pos.moved_piece(move);
givesCheck = gives_check(pos, move);
- // Skip quiet moves if movecount exceeds our FutilityMoveCount threshold
- moveCountPruning = depth < 16 * ONE_PLY
- && moveCount >= FutilityMoveCounts[improving][depth / ONE_PLY];
-
// Step 13. Extensions (~70 Elo)
// Singular extension search (~60 Elo). If all moves but one fail low on a
&& pos.non_pawn_material(us)
&& bestValue > VALUE_MATED_IN_MAX_PLY)
{
+ // Skip quiet moves if movecount exceeds our FutilityMoveCount threshold
+ moveCountPruning = depth < 16 * ONE_PLY
+ && moveCount >= FutilityMoveCounts[improving][depth / ONE_PLY];
+
if ( !captureOrPromotion
&& !givesCheck
&& !pos.advanced_pawn_push(move))