My Project
effect5x3.cc
Go to the documentation of this file.
1/* effect5x3.cc
2 */
5
8{
15}
16
19 Square king)
20{
21 return makeProgressArea(alt(defense), state, king)
22 + makeProgressStand(alt(defense), state);
23}
24
27 Square king)
28{
29 const Square center = Centering5x3::adjustCenter(king);
30
31 const int min_x = center.x() - 2;
32 const int min_y = center.y() - 1;
33
34 // 利き
35 int sum_effect = 0;
36
37 for (int dx=0; dx<5; ++dx)
38 {
39 for (int dy=0; dy<3; ++dy)
40 {
41 const Square target(min_x+dx,min_y+dy);
42 sum_effect += state.countEffect(attack, target) *
43 Effect5x3_Table.getAttackEffect(attack,king,dx,dy);
44 }
45 }
46 return sum_effect / 2;
47}
48
51{
52 // 持駒
53 int sum_pieces = 0;
54 sum_pieces += state.countPiecesOnStand<PAWN>(attack)*Effect5x3Table::StandPAWN;
55 sum_pieces += state.countPiecesOnStand<LANCE>(attack)*Effect5x3Table::StandLANCE;
56 sum_pieces += state.countPiecesOnStand<KNIGHT>(attack)*Effect5x3Table::StandKNIGHT;
57 sum_pieces += state.countPiecesOnStand<SILVER>(attack)*Effect5x3Table::StandSILVER;
58 sum_pieces += state.countPiecesOnStand<GOLD>(attack)*Effect5x3Table::StandGOLD;
59 sum_pieces += state.countPiecesOnStand<BISHOP>(attack)*Effect5x3Table::StandBISHOP;
60 sum_pieces += state.countPiecesOnStand<ROOK>(attack)*Effect5x3Table::StandROOK;
61 return sum_pieces;
62}
63
65Effect5x3::updateStand(int& old_stand, Move last_move)
66{
67 if (last_move.isDrop()) {
68 const Ptype ptype = last_move.ptype();
69 old_stand -= Effect5x3_Table.piecesOnStand(ptype);
70 return;
71 }
72 const Ptype ptype = last_move.capturePtype();
73 if (ptype == PTYPE_EMPTY) {
74 return;
75 }
76 old_stand += Effect5x3_Table.piecesOnStand(unpromote(ptype));
77}
78
80Effect5x3::update(const NumEffectState& new_state, Move last_move)
81{
82 const Player pl = last_move.player();
83 updateStand(stand_progresses[alt(pl)], last_move);
84
85 const Square kb = new_state.kingSquare<BLACK>(), kw = new_state.kingSquare<WHITE>();
86 BoardMask mb = new_state.changedEffects(BLACK), mw = new_state.changedEffects(WHITE);
87 bool king_move = last_move.ptype() == KING;
88 if ((king_move && new_state.turn() == BLACK) || mb.anyInRange(Board_Mask_Table5x3_Center.mask(kw)))
89 area_progresses[WHITE]=makeProgressArea(BLACK,new_state, kw);
90 if ((king_move && new_state.turn() == WHITE) || mw.anyInRange(Board_Mask_Table5x3_Center.mask(kb)))
91 area_progresses[BLACK]=makeProgressArea(WHITE,new_state, kb);
92
93 progresses[BLACK]=area_progresses[BLACK]+stand_progresses[BLACK];
94 progresses[WHITE]=area_progresses[WHITE]+stand_progresses[WHITE];
95}
96
98Effect5x3::expect(const NumEffectState&, Move move) const
99{
100 Effect5x3 new_progress = *this;
101 if (move.capturePtype() != PTYPE_EMPTY) {
102 const Player alt_pl = alt(move.player());
103 int old = stand_progresses[alt_pl];
104 updateStand(new_progress.stand_progresses[alt_pl], move);
105 new_progress.progresses[alt_pl] += new_progress.stand_progresses[alt_pl] - old;
106 }
107 return new_progress;
108}
109
110/* ------------------------------------------------------------------------- */
111
114{
115 progress_bonuses[BLACK]=makeProgressAreaBonus<WHITE>(state, state.kingSquare<BLACK>());
116 progress_bonuses[WHITE]=makeProgressAreaBonus<BLACK>(state, state.kingSquare<WHITE>());
117 effect_mask[BLACK] = makeEffectMask<BLACK>(state);
118 effect_mask[WHITE] = makeEffectMask<WHITE>(state);
120}
121
122template <osl::Player Defense>
125{
126 const Square king =
127 state.kingSquare<Defense>();
128 const Square center =
130
131 const int min_x = center.x() - 2;
132 const int min_y = center.y() - 1;
133
134 PieceMask mask;
135 for (int dx = 0; dx < 5; ++dx)
136 {
137 for (int dy = 0; dy < 3; ++dy)
138 {
139 const Square target(min_x+dx, min_y+dy);
140 mask = mask | state.effectSetAt(target);
141 }
142 }
143 return mask;
144}
145
146inline
149{
150 const int a = state.countEffect(attack, target);
151 if (a <= 1)
152 return a;
153 if (state.countEffect(alt(attack), target) > 0
154 || state.pieceAt(target).isOnBoardByOwner(attack))
155 return 1;
156 return 2;
157}
158
159namespace osl
160{
161 namespace
162 {
163 template <Player P>
164 int countPawnLanceKnight(const NumEffectState& state, Square target)
165 {
166 // effect is max 2, pawn and lance cannot have the effect
167 // to a position at the same time so this is OK
169 const Piece pd = state.pieceAt(d);
170
171 // pawn and lance
172 int count = 0;
173 if (pd.ptypeO() == newPtypeO(P,PAWN))
174 ++count;
175 else if (pd.ptypeO() == newPtypeO(P,LANCE))
176 ++count;
177 else if (pd.isEmpty())
178 {
179 if (state.hasLongEffectAt<LANCE>(P, target))
180 ++count;
181 }
182 else if (pd.isEdge())
183 return 0;
184
185 // knight
187 if (pdl.ptypeO() == newPtypeO(P,KNIGHT))
188 return count+1;
190 if (pdr.ptypeO() == newPtypeO(P,KNIGHT))
191 return count+1;
192 return count;
193 }
194 }
195}
196
197template <osl::Player Attack, bool AlwaysPromotable, bool AlwaysNotPromotable>
200 Square center)
201{
202 const int min_x = center.x() - 2;
203 const int min_y = center.y() - 1;
204
205 // 利き
206 int sum_effect = 0;
207
208 for (int dy = 0; dy < 3; ++dy)
209 {
210 const Square target(king.x(), min_y + dy);
211 int effect = attackEffect3(state, Attack, target) * 2;
212 if (effect > 0)
213 {
214 if (! AlwaysPromotable
215 && (AlwaysNotPromotable || !target.canPromote<Attack>()) )
216 {
217 effect -= countPawnLanceKnight<Attack>(state, target);
218 assert(effect >= 0);
219 }
220 sum_effect += effect *
221 Effect5x3_Table.getAttackEffect(Attack, king, target.x() - min_x, dy) / 2;
222
223 }
224 }
225 for (int x = king.x() - 1; x >= min_x; --x)
226 {
227 int y_count = 0;
228 int sum = 0;
229 for (int dy = 0; dy < 3; ++dy)
230 {
231 const Square target(x, min_y + dy);
232 int effect = attackEffect3(state, Attack, target) * 2;
233 if (effect > 0)
234 {
235 if (! AlwaysPromotable
236 && (AlwaysNotPromotable || !target.canPromote<Attack>()) )
237 {
238 if (king.x() - x > 1)
239 effect = 0;
240 else
241 effect -= countPawnLanceKnight<Attack>(state, target);
242 assert(effect >= 0);
243 }
244 sum += effect *
245 Effect5x3_Table.getAttackEffect(Attack, king, x - min_x, dy) / 2;
246 y_count++;
247 }
248 }
249 sum_effect += sum;
250 if (y_count == 3)
251 {
252 sum_effect += sum;
253 break;
254 }
255 }
256 for (int x = king.x() + 1; x < min_x + 5; ++x)
257 {
258 int y_count = 0;
259 int sum = 0;
260 for (int dy = 0; dy < 3; ++dy)
261 {
262 const Square target(x, min_y + dy);
263 int effect = attackEffect3(state, Attack, target) * 2;
264 if (effect > 0)
265 {
266 if (! AlwaysPromotable
267 && (AlwaysNotPromotable || !target.canPromote<Attack>()) )
268 {
269 if (x - king.x() > 1)
270 effect = 0;
271 else
272 effect -= countPawnLanceKnight<Attack>(state, target);
273 assert(effect >= 0);
274 }
275 sum += effect *
276 Effect5x3_Table.getAttackEffect(Attack, king, x - min_x, dy) / 2;
277 y_count++;
278 }
279 }
280 sum_effect += sum;
281 if (y_count == 3)
282 {
283 sum_effect += sum;
284 break;
285 }
286 }
287 return sum_effect / 2;
288}
289
290template <osl::Player Attack>
293 Square king)
294{
295 const Square center = Centering5x3::adjustCenter(king);
296
297 const bool always_promotable = center.squareForBlack<Attack>().y() <= 2;
298 if (always_promotable)
299 return makeProgressAreaBonus<Attack,true,false>(state, king, center);
300 const bool always_notpromotable = center.squareForBlack<Attack>().y() >= 5;
301 if (always_notpromotable)
302 return makeProgressAreaBonus<Attack,false,true>(state, king, center);
303 return makeProgressAreaBonus<Attack,false,false>(state, king, center);
304}
305
307Effect5x3WithBonus::update(const NumEffectState& new_state, Move last_move)
308{
309 Effect5x3::update(new_state, last_move);
310
311 const Square kb = new_state.kingSquare<BLACK>(), kw = new_state.kingSquare<WHITE>();
312 BoardMask mask = new_state.changedEffects();
313 mask.set(last_move.to()); mask.set(last_move.from());
314
315 const bool update_black = mask.anyInRange(Board_Mask_Table5x3_Center.mask(kb));
316 const bool update_white = mask.anyInRange(Board_Mask_Table5x3_Center.mask(kw));
317
318 if (update_black)
319 {
320 progress_bonuses[BLACK]=makeProgressAreaBonus<WHITE>(new_state,kb);
321 effect_mask[BLACK] = makeEffectMask<BLACK>(new_state);
322 }
323 if (update_white)
324 {
325 progress_bonuses[WHITE]=makeProgressAreaBonus<BLACK>(new_state,kw);
326 effect_mask[WHITE] = makeEffectMask<WHITE>(new_state);
327 }
328 updateProgressBonuses(new_state, update_black, update_white);
329}
330
333{
334 Effect5x3WithBonus new_progress = *this;
335 if (move.capturePtype() != PTYPE_EMPTY) {
336 const Player alt_pl = alt(move.player());
337 int old = stand_progresses[playerToIndex(alt_pl)];
338 new_progress.updateStand(alt_pl, move);
339 new_progress.progresses[playerToIndex(alt_pl)] += new_progress.stand_progresses[playerToIndex(alt_pl)] - old;
340 }
341 return new_progress;
342}
343
345Effect5x3WithBonus::updateProgressBonuses(const NumEffectState& state, bool update_black, bool update_white)
346{
347 if (update_black && progress_bonuses[BLACK] != 0)
348 {
349 const int pieces = countEffectPieces(state, WHITE);
350 progress_bonuses[BLACK] =
351 std::min(pieces * pieces * 4,
352 progress_bonuses[BLACK]);
353 }
354 if (update_white && progress_bonuses[WHITE] != 0)
355 {
356 const int pieces = countEffectPieces(state, BLACK);
357 progress_bonuses[WHITE] =
358 std::min(pieces * pieces * 4,
359 progress_bonuses[WHITE]);
360 }
361}
362
365{
366 PieceMask mask = effect5x3Mask(alt(attack));
367 mask = mask & state.piecesOnBoard(attack);
368 return mask.countBit();
369}
370
371/* ------------------------------------------------------------------------- */
372// ;;; Local Variables:
373// ;;; mode:c++
374// ;;; c-basic-offset:2
375// ;;; End:
圧縮していない moveの表現 .
Definition: basic_type.h:1052
Ptype ptype() const
Definition: basic_type.h:1155
Player player() const
Definition: basic_type.h:1195
bool isDrop() const
Definition: basic_type.h:1150
Ptype capturePtype() const
Definition: basic_type.h:1180
const Square to() const
Definition: basic_type.h:1132
const Square from() const
Definition: basic_type.h:1125
利きを持つ局面
const NumBitmapEffect effectSetAt(Square sq) const
const BoardMask changedEffects(Player pl) const
int countEffect(Player player, Square target) const
利きの数を数える.
bool hasLongEffectAt(Player P, Square to) const
あるマスにPTYPEの長い利きがあるかどうか.
const PieceMask & piecesOnBoard(Player p) const
駒番号のビットセット.
Definition: pieceMask.h:21
PtypeO ptypeO() const
Definition: basic_type.h:824
bool isEmpty() const
Definition: basic_type.h:913
bool isEdge() const
Definition: basic_type.h:919
bool isOnBoardByOwner() const
piece がプレイヤーPの持ち物でかつボード上にある駒の場合は true.
Definition: basic_type.h:852
Player turn() const
Definition: simpleState.h:220
Square kingSquare() const
Definition: simpleState.h:94
int countPiecesOnStand(Player pl, Ptype ptype) const
持駒の枚数を数える
Definition: simpleState.h:182
const Piece pieceAt(Square sq) const
Definition: simpleState.h:167
int y() const
将棋としてのY座標を返す.
Definition: basic_type.h:567
bool canPromote() const
Definition: basic_type.h:659
const Square squareForBlack(Player player) const
Definition: basic_type.h:598
int x() const
将棋としてのX座標を返す.
Definition: basic_type.h:563
const BoardMask & mask(Square p) const
p中心の5x3 の範囲のbitを立てたもの, centering
Definition: boardMask.h:133
void set(unsigned int i)
Definition: boardMask.h:40
bool anyInRange(const BoardMask &mask) const
Definition: boardMask.h:57
unsigned int piecesOnStand(Ptype ptype) const
持駒のPtypeごとの寄与を表すテーブルの参照.
unsigned int getAttackEffect(Player pl, Square pos, int x, int y) const
const BoardMaskTable5x3Center Board_Mask_Table5x3_Center
Definition: tables.cc:121
int min(Player p, int v1, int v2)
Definition: evalTraits.h:92
Effect5x3Table Effect5x3_Table
Ptype
駒の種類を4ビットでコード化する
Definition: basic_type.h:84
@ ROOK
Definition: basic_type.h:100
@ BISHOP
Definition: basic_type.h:99
@ PAWN
Definition: basic_type.h:95
@ KING
Definition: basic_type.h:93
@ KNIGHT
Definition: basic_type.h:97
@ PTYPE_EMPTY
Definition: basic_type.h:85
@ SILVER
Definition: basic_type.h:98
@ GOLD
Definition: basic_type.h:94
@ LANCE
Definition: basic_type.h:96
Ptype unpromote(Ptype ptype)
ptypeがpromote後の型の時に,promote前の型を返す. promoteしていない型の時はそのまま返す
Definition: basic_type.h:157
constexpr int playerToIndex(Player player)
Definition: basic_type.h:16
Player
Definition: basic_type.h:8
@ WHITE
Definition: basic_type.h:10
@ BLACK
Definition: basic_type.h:9
constexpr Player alt(Player player)
Definition: basic_type.h:13
PtypeO newPtypeO(Player player, Ptype ptype)
Definition: basic_type.h:211
static const Square adjustCenter(Square src)
Definition: centering5x3.h:23
int countEffectPieces(const NumEffectState &state, Player attack) const
Definition: effect5x3.cc:364
void updateStand(Player pl, Move m)
Definition: effect5x3.h:113
Effect5x3WithBonus(const NumEffectState &state)
Definition: effect5x3.cc:113
static int attackEffect3(const NumEffectState &state, Player attack, Square target)
Definition: effect5x3.cc:148
Effect5x3WithBonus expect(const NumEffectState &state, Move move) const
Definition: effect5x3.cc:332
static int makeProgressAreaBonus(const NumEffectState &state, Square king)
Definition: effect5x3.cc:292
void updateProgressBonuses(const NumEffectState &state, bool black=true, bool white=true)
Definition: effect5x3.cc:345
static PieceMask makeEffectMask(const NumEffectState &state)
void update(const NumEffectState &new_state, Move last_move)
Definition: effect5x3.cc:307
CArray< PieceMask, 2 > effect_mask
Definition: effect5x3.h:116
CArray< int, 2 > progress_bonuses
Definition: effect5x3.h:115
玉の周囲5x3の領域の利きの数と持駒から計算した進行度.
Definition: effect5x3.h:27
static int makeProgressStand(Player attack, const NumEffectState &state)
Definition: effect5x3.cc:50
CArray< int, 2 > progresses
Definition: effect5x3.h:71
CArray< int, 2 > area_progresses
Definition: effect5x3.h:71
CArray< int, 2 > stand_progresses
Definition: effect5x3.h:71
static int makeProgressArea(Player attack, const NumEffectState &state, Square king)
Definition: effect5x3.cc:26
void update(const NumEffectState &new_state, Move last_move)
Definition: effect5x3.cc:80
static void updateStand(int &old_stand, Move last_move)
Definition: effect5x3.cc:65
Effect5x3(const NumEffectState &state)
Definition: effect5x3.cc:7
Effect5x3 expect(const NumEffectState &state, Move move) const
Definition: effect5x3.cc:98
static int makeProgressAll(Player defense, const NumEffectState &state, Square king)
Definition: effect5x3.cc:18