Rev 154 | Go to most recent revision | Show entire file | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed
| Rev 154 | Rev 169 | ||
|---|---|---|---|
| Line 4... | Line 4... | ||
| 4 | Copyright (C) 2008-2015 Marco Costalba, Joona Kiiski, Tord Romstad |
4 | Copyright (C) 2008-2015 Marco Costalba, Joona Kiiski, Tord Romstad |
| 5 | Copyright (C) 2015- |
5 | Copyright (C) 2015-2018 Marco Costalba, Joona Kiiski, Gary Linscott, Tord Romstad |
| 6 | 6 | ||
| 7 | Stockfish is free software: you can redistribute it and/or modify |
7 | Stockfish is free software: you can redistribute it and/or modify |
| 8 | it under the terms of the GNU General Public License as published by |
8 | it under the terms of the GNU General Public License as published by |
| 9 | the Free Software Foundation, either version 3 of the License, or |
9 | the Free Software Foundation, either version 3 of the License, or |
| 10 | (at your option) any later version. |
10 | (at your option) any later version. |
| Line 19... | Line 19... | ||
| 19 | */ |
19 | */ |
| 20 | 20 | ||
| 21 | #ifndef MOVEPICK_H_INCLUDED |
21 | #ifndef MOVEPICK_H_INCLUDED |
| 22 | #define MOVEPICK_H_INCLUDED |
22 | #define MOVEPICK_H_INCLUDED |
| 23 | 23 | ||
| 24 | #include < |
24 | #include <array> |
| 25 | #include < |
25 | #include <limits> |
| 26 | 26 | ||
| 27 | #include "movegen.h" |
27 | #include "movegen.h" |
| 28 | #include "position.h" |
28 | #include "position.h" |
| 29 | #include "types.h" |
29 | #include "types.h" |
| 30 | 30 | ||
| - | 31 | /// StatBoards is a generic 2-dimensional array used to store various statistics |
|
| - | 32 | template<int Size1, int Size2, typename T = int16_t> |
|
| - | 33 | struct StatBoards : public std::array<std::array<T, Size2>, Size1> { |
|
| 31 | 34 | ||
| 32 | /// The Stats struct stores moves statistics. According to the template parameter |
- | |
| 33 | /// the class can store History and Countermoves. History records how often |
- | |
| 34 | /// different moves have been successful or unsuccessful during the current search |
- | |
| 35 |
|
35 | void fill(const T& v) { |
| 36 |
|
36 | T* p = &(*this)[0][0]; |
| 37 |
|
37 | std::fill(p, p + sizeof(*this) / sizeof(*p), v); |
| 38 | /// different origin but same destination and piece will be considered identical. |
- | |
| 39 | template<typename T, bool CM = false> |
- | |
| 40 |
|
38 | } |
| 41 | 39 | ||
| 42 |
|
40 | void update(T& entry, int bonus, const int D) { |
| 43 | 41 | ||
| 44 | const T* operator[](Piece pc) const { return table[pc]; } |
- | |
| 45 |
|
42 | assert(abs(bonus) <= D); // Ensure range is [-32 * D, 32 * D] |
| 46 |
|
43 | assert(abs(32 * D) < (std::numeric_limits<T>::max)()); // Ensure we don't overflow |
| 47 | void update(Piece pc, Square to, Move m) { table[pc][to] = m; } |
- | |
| 48 | void update(Piece pc, Square to, Value v) { |
- | |
| 49 | 44 | ||
| 50 |
|
45 | entry += bonus * 32 - entry * abs(bonus) / D; |
| 51 | return; |
- | |
| 52 | 46 | ||
| 53 | table[pc][to] -= table[pc][to] * abs(int(v)) / (CM ? 936 : 324); |
- | |
| 54 |
|
47 | assert(abs(entry) <= 32 * D); |
| 55 | } |
48 | } |
| - | 49 | }; |
|
| 56 | 50 | ||
| - | 51 | /// StatCubes is a generic 3-dimensional array used to store various statistics |
|
| - | 52 | template<int Size1, int Size2, int Size3, typename T = int16_t> |
|
| - | 53 | struct StatCubes : public std::array<std::array<std::array<T, Size3>, Size2>, Size1> { |
|
| - | 54 | ||
| - | 55 | void fill(const T& v) { |
|
| - | 56 | T* p = &(*this)[0][0][0]; |
|
| - | 57 | std::fill(p, p + sizeof(*this) / sizeof(*p), v); |
|
| 57 |
|
58 | } |
| - | 59 | ||
| - | 60 | void update(T& entry, int bonus, const int D, const int W) { |
|
| - | 61 | ||
| - | 62 | assert(abs(bonus) <= D); // Ensure range is [-W * D, W * D] |
|
| - | 63 | assert(abs(W * D) < (std::numeric_limits<T>::max)()); // Ensure we don't overflow |
|
| - | 64 | ||
| - | 65 | entry += bonus * W - entry * abs(bonus) / D; |
|
| - | 66 | ||
| 58 |
|
67 | assert(abs(entry) <= W * D); |
| - | 68 | } |
|
| 59 | }; |
69 | }; |
| 60 | 70 | ||
| 61 | typedef Stats<Move> MoveStats; |
- | |
| 62 |
|
71 | /// ButterflyBoards are 2 tables (one for each color) indexed by the move's from |
| 63 |
|
72 | /// and to squares, see chessprogramming.wikispaces.com/Butterfly+Boards |
| 64 | typedef |
73 | typedef StatBoards<COLOR_NB, int(SQUARE_NB) * int(SQUARE_NB)> ButterflyBoards; |
| 65 | 74 | ||
| - | 75 | /// PieceToBoards are addressed by a move's [piece][to] information |
|
| 66 |
|
76 | typedef StatBoards<PIECE_NB, SQUARE_NB> PieceToBoards; |
| 67 | 77 | ||
| 68 |
|
78 | /// CapturePieceToBoards are addressed by a move's [piece][to][captured piece type] information |
| 69 |
|
79 | typedef StatCubes<PIECE_NB, SQUARE_NB, PIECE_TYPE_NB> CapturePieceToBoards; |
| 70 | void update(Color c, Move m, Value v) { |
- | |
| 71 | 80 | ||
| - | 81 | /// ButterflyHistory records how often quiet moves have been successful or |
|
| - | 82 | /// unsuccessful during the current search, and is used for reduction and move |
|
| 72 |
|
83 | /// ordering decisions. It uses ButterflyBoards as backing store. |
| 73 |
|
84 | struct ButterflyHistory : public ButterflyBoards { |
| 74 | 85 | ||
| 75 |
|
86 | void update(Color c, Move m, int bonus) { |
| 76 |
|
87 | StatBoards::update((*this)[c][from_to(m)], bonus, 324); |
| - | 88 | } |
|
| - | 89 | }; |
|
| 77 | 90 | ||
| 78 |
|
91 | /// PieceToHistory is like ButterflyHistory, but is based on PieceToBoards |
| - | 92 | struct PieceToHistory : public PieceToBoards { |
|
| - | 93 | ||
| - | 94 | void update(Piece pc, Square to, int bonus) { |
|
| 79 |
|
95 | StatBoards::update((*this)[pc][to], bonus, 936); |
| 80 | } |
96 | } |
| - | 97 | }; |
|
| 81 | 98 | ||
| - | 99 | /// CapturePieceToHistory is like PieceToHistory, but is based on CapturePieceToBoards |
|
| - | 100 | struct CapturePieceToHistory : public CapturePieceToBoards { |
|
| 82 | private: |
101 | |
| - | 102 | void update(Piece pc, Square to, PieceType captured, int bonus) { |
|
| 83 |
|
103 | StatCubes::update((*this)[pc][to][captured], bonus, 324, 2); |
| - | 104 | } |
|
| 84 | }; |
105 | }; |
| - | 106 | ||
| - | 107 | /// CounterMoveHistory stores counter moves indexed by [piece][to] of the previous |
|
| - | 108 | /// move, see chessprogramming.wikispaces.com/Countermove+Heuristic |
|
| - | 109 | typedef StatBoards<PIECE_NB, SQUARE_NB, Move> CounterMoveHistory; |
|
| - | 110 | ||
| - | 111 | /// ContinuationHistory is the history of a given pair of moves, usually the |
|
| - | 112 | /// current one given a previous one. History table is based on PieceToBoards |
|
| - | 113 | /// instead of ButterflyBoards. |
|
| - | 114 | typedef StatBoards<PIECE_NB, SQUARE_NB, PieceToHistory> ContinuationHistory; |
|
| 85 | 115 | ||
| 86 | 116 | ||
| 87 | /// MovePicker class is used to pick one pseudo legal move at a time from the |
117 | /// MovePicker class is used to pick one pseudo legal move at a time from the |
| 88 | /// current position. The most important method is next_move(), which returns a |
118 | /// current position. The most important method is next_move(), which returns a |
| 89 | /// new pseudo legal move each time it is called, until there are no moves left, |
119 | /// new pseudo legal move each time it is called, until there are no moves left, |
| 90 | /// when MOVE_NONE is returned. In order to improve the efficiency of the alpha |
120 | /// when MOVE_NONE is returned. In order to improve the efficiency of the alpha |
| 91 | /// beta algorithm, MovePicker attempts to return the moves which are most likely |
121 | /// beta algorithm, MovePicker attempts to return the moves which are most likely |
| 92 | /// to get a cut-off first. |
122 | /// to get a cut-off first. |
| 93 | namespace Search { struct Stack; } |
- | |
| 94 | 123 | ||
| 95 | class MovePicker { |
124 | class MovePicker { |
| 96 | public: |
125 | public: |
| 97 | MovePicker(const MovePicker&) = delete; |
126 | MovePicker(const MovePicker&) = delete; |
| 98 | MovePicker& operator=(const MovePicker&) = delete; |
127 | MovePicker& operator=(const MovePicker&) = delete; |
| 99 | - | ||
| 100 | MovePicker(const Position&, Move, |
128 | MovePicker(const Position&, Move, Value, const CapturePieceToHistory*); |
| 101 | MovePicker(const Position&, Move, Depth, Square); |
129 | MovePicker(const Position&, Move, Depth, const ButterflyHistory*, const CapturePieceToHistory*, Square); |
| 102 | MovePicker(const Position&, Move, Depth, |
130 | MovePicker(const Position&, Move, Depth, const ButterflyHistory*, const CapturePieceToHistory*, const PieceToHistory**, Move, Move*); |
| 103 | - | ||
| 104 | Move next_move(); |
131 | Move next_move(bool skipQuiets = false); |
| 105 | 132 | ||
| 106 | private: |
133 | private: |
| 107 | template<GenType> void score(); |
134 | template<GenType> void score(); |
| 108 | ExtMove* begin() { return cur; } |
135 | ExtMove* begin() { return cur; } |
| 109 | ExtMove* end() { return endMoves; } |
136 | ExtMove* end() { return endMoves; } |
| 110 | 137 | ||
| 111 | const Position& pos; |
138 | const Position& pos; |
| - | 139 | const ButterflyHistory* mainHistory; |
|
| - | 140 | const CapturePieceToHistory* captureHistory; |
|
| 112 | const |
141 | const PieceToHistory** contHistory; |
| 113 | Move |
142 | Move ttMove, countermove, killers[2]; |
| 114 |
|
143 | ExtMove *cur, *endMoves, *endBadCaptures; |
| 115 |
|
144 | int stage; |
| 116 | Square recaptureSquare; |
145 | Square recaptureSquare; |
| 117 | Value threshold; |
146 | Value threshold; |
| 118 |
|
147 | Depth depth; |
| 119 | ExtMove *cur, *endMoves, *endBadCaptures; |
- | |
| 120 | ExtMove moves[MAX_MOVES]; |
148 | ExtMove moves[MAX_MOVES]; |
| 121 | }; |
149 | }; |
| 122 | 150 | ||
| 123 | #endif // #ifndef MOVEPICK_H_INCLUDED |
151 | #endif // #ifndef MOVEPICK_H_INCLUDED |