1
0
Fork 0
mirror of https://github.com/sockspls/badfish synced 2025-04-30 16:53:09 +00:00

In movepicker increase priority for moves that evade a capture

This idea is a mix of koivisto idea of threat history and heuristic that
was simplified some time ago in LMR - decreasing reduction for moves that evade a capture.
Instead of doing so in LMR this patch does it in movepicker - to do this it
calculates squares that are attacked by different piece types and pieces that are located
on this squares and boosts up weight of moves that make this pieces land on a square that is not under threat.
Boost is greater for pieces with bigger material values.
Special thanks to koivisto and seer authors for explaining me ideas behind threat history.

Passed STC:
https://tests.stockfishchess.org/tests/view/62406e473b32264b9aa1478b
LLR: 2.94 (-2.94,2.94) <0.00,2.50>
Total: 19816 W: 5320 L: 5072 D: 9424
Ptnml(0-2): 86, 2165, 5172, 2385, 100

Passed LTC:
https://tests.stockfishchess.org/tests/view/62407f2e3b32264b9aa149c8
LLR: 2.94 (-2.94,2.94) <0.50,3.00>
Total: 51200 W: 13805 L: 13500 D: 23895
Ptnml(0-2): 44, 5023, 15164, 5322, 47

closes https://github.com/official-stockfish/Stockfish/pull/3970

bench 7736491
This commit is contained in:
Michael Chaly 2022-03-28 14:15:56 +03:00 committed by Joost VandeVondele
parent 910cf8b218
commit 08e0f52b77

View file

@ -97,6 +97,44 @@ MovePicker::MovePicker(const Position& p, Move ttm, Value th, Depth d, const Cap
&& pos.see_ge(ttm, threshold));
}
//squares threatened by pawn attacks
template <Color Us>
Bitboard threatsByPawn (const Position& pos)
{
return pawn_attacks_bb<Us>(pos.pieces(Us, PAWN));
}
//squares threatened by minor attacks
template <Color Us>
Bitboard threatsByMinor (const Position& pos)
{
Bitboard our = pos.pieces(Us, KNIGHT, BISHOP);
Bitboard threats = 0;
while (our)
{
Square s = pop_lsb(our);
if (type_of(pos.piece_on(s)) == KNIGHT)
threats |= attacks_bb<KNIGHT>(s, pos.pieces());
else
threats |= attacks_bb<BISHOP>(s, pos.pieces());
}
return threats;
}
//squares threatened by rook attacks
template <Color Us>
Bitboard threatsByRook (const Position& pos)
{
Bitboard our = pos.pieces(Us, ROOK);
Bitboard threats = 0;
while (our)
{
Square s = pop_lsb(our);
threats |= attacks_bb<ROOK>(s, pos.pieces());
}
return threats;
}
/// MovePicker::score() assigns a numerical value to each move in a list, used
/// for sorting. Captures are ordered by Most Valuable Victim (MVV), preferring
/// captures with a good history. Quiets moves are ordered using the histories.
@ -105,6 +143,35 @@ void MovePicker::score() {
static_assert(Type == CAPTURES || Type == QUIETS || Type == EVASIONS, "Wrong type");
Bitboard threatened, threatenedByPawn, threatenedByMinor, threatenedByRook;
if constexpr (Type == QUIETS)
{
// squares threatened by pawns
threatenedByPawn = pos.side_to_move() == WHITE ? threatsByPawn<BLACK>(pos) : threatsByPawn<WHITE>(pos);
// squares threatened by minors or pawns
threatenedByMinor = pos.side_to_move() == WHITE ? threatsByMinor<BLACK>(pos) : threatsByMinor<WHITE>(pos);
threatenedByMinor |= threatenedByPawn;
// squares threatened by rooks, minors or pawns
threatenedByRook = pos.side_to_move() == WHITE ? threatsByRook<BLACK>(pos) : threatsByRook<WHITE>(pos);
threatenedByRook |= threatenedByMinor;
// pieces threatened by pieces of lesser material value
threatened = pos.side_to_move() == WHITE ? ((pos.pieces(WHITE, QUEEN) & threatenedByRook) |
(pos.pieces(WHITE, ROOK) & threatenedByMinor) |
(pos.pieces(WHITE, KNIGHT, BISHOP) & threatenedByPawn))
: ((pos.pieces(BLACK, QUEEN) & threatenedByRook) |
(pos.pieces(BLACK, ROOK) & threatenedByMinor) |
(pos.pieces(BLACK, KNIGHT, BISHOP) & threatenedByPawn));
}
else
{
// Silence unused variable warning
(void) threatened;
(void) threatenedByPawn;
(void) threatenedByMinor;
(void) threatenedByRook;
}
for (auto& m : *this)
if constexpr (Type == CAPTURES)
m.value = 6 * int(PieceValue[MG][pos.piece_on(to_sq(m))])
@ -115,7 +182,13 @@ void MovePicker::score() {
+ 2 * (*continuationHistory[0])[pos.moved_piece(m)][to_sq(m)]
+ (*continuationHistory[1])[pos.moved_piece(m)][to_sq(m)]
+ (*continuationHistory[3])[pos.moved_piece(m)][to_sq(m)]
+ (*continuationHistory[5])[pos.moved_piece(m)][to_sq(m)];
+ (*continuationHistory[5])[pos.moved_piece(m)][to_sq(m)]
+ (threatened & from_sq(m) ?
(type_of(pos.piece_on(from_sq(m))) == QUEEN && !(to_sq(m) & threatenedByRook) ? 50000
: type_of(pos.piece_on(from_sq(m))) == ROOK && !(to_sq(m) & threatenedByMinor) ? 25000
: !(to_sq(m) & threatenedByPawn) ? 15000
: 0)
: 0);
else // Type == EVASIONS
{