8 #include <boost/filesystem/operations.hpp>
16 template <
class Opening>
19 template <
class Opening>
26 return composeValue(opening_eval.expect(state, move),
27 endgame_eval.expect(state, move),
31 defense_effect.progress16(
WHITE),
32 minor_piece_bonus.value(progress16(),
33 progress16bonus(
BLACK),
34 progress16bonus(
WHITE)),
35 progress_independent_bonus,
36 progress_dependent_bonus);
39 template <
class Opening>
46 filename = filename_given;
48 filename = OslConfig::home();
49 filename +=
"/data/progresseval.txt";
51 if (boost::filesystem::exists(filename.c_str())) {
53 std::cerr <<
"loading " << filename <<
"\n";
54 CArray<int, AdjustableDimension> w;
55 FILE *fp = fopen(filename.c_str(),
"r");
56 for (
size_t i=0; i<w.size(); ++i) {
57 if (fscanf(fp,
"%d", &w[i]) != 1) {
58 std::cerr << filename <<
" read failed " << i <<
"\n";
70 capture_values[i] = composeValue(opening_eval_t::captureValue(ptypeo), 0,
71 Progress16(0), Progress16(0), Progress16(0),
72 Progress16(0), Progress16(0), 0, 0, 0);
76 template <
class Opening>
80 opening_eval_t::resetWeights(w);
84 template <
class Opening>
87 : opening_eval(state), endgame_eval(state),
88 current_progress(state), defense_effect(state),
89 minor_piece_bonus(state), major_pieces(0),
93 i < PtypeTraits<ROOK>::indexLimit; ++i)
99 i < PtypeTraits<BISHOP>::indexLimit; ++i)
106 initializeCheckPiece<BLACK, ROOK>(state);
107 initializeCheckPiece<BLACK, BISHOP>(state);
108 initializeCheckPiece<BLACK, GOLD>(state);
109 initializeCheckPiece<BLACK, SILVER>(state);
110 initializeCheckPiece<BLACK, LANCE>(state);
111 initializeCheckPiece<WHITE, ROOK>(state);
112 initializeCheckPiece<WHITE, BISHOP>(state);
113 initializeCheckPiece<WHITE, GOLD>(state);
114 initializeCheckPiece<WHITE, SILVER>(state);
115 initializeCheckPiece<WHITE, LANCE>(state);
132 progress_independent_bonus += calculateMiddleKingBonus<BLACK>(state);
133 progress_independent_bonus += calculateMiddleKingBonus<WHITE>(state);
137 template <
class Opening>
138 template<osl::Player P, osl::Ptype PTYPE>
141 const NumEffectState &state)
143 if (state.hasPieceOnStand<PTYPE>(P))
145 int count = state.countPiecesOnStand(P, PTYPE);
146 initializeCheckPieceDir<P, PTYPE, UL, LONG_UL>(state,
count);
147 initializeCheckPieceDir<P, PTYPE, U, LONG_U>(state,
count);
148 initializeCheckPieceDir<P, PTYPE, UR, LONG_UR>(state,
count);
149 initializeCheckPieceDir<P, PTYPE, L, LONG_L>(state,
count);
150 initializeCheckPieceDir<P, PTYPE, R, LONG_R>(state,
count);
151 initializeCheckPieceDir<P, PTYPE, DL, LONG_DL>(state,
count);
152 initializeCheckPieceDir<P, PTYPE, D, LONG_D>(state,
count);
153 initializeCheckPieceDir<P, PTYPE, DR, LONG_DR>(state,
count);
157 template <
class Opening>
158 template<osl::Player P, osl::Ptype PTYPE, osl::Direction Dir, osl::Direction LongDir>
161 const NumEffectState &,
166 can_check_pieces[P][Dir] =
count;
169 template <
class Opening>
173 using namespace osl::mobility;
176 i<PtypeTraits<ROOK>::indexLimit;++i){
177 Piece p=state.pieceOf(i);
179 int vc= RookMobility::countVerticalAll(
BLACK,state,p);
180 int hc= RookMobility::countHorizontalAll(
BLACK,state,p);
191 int vc= RookMobility::countVerticalAll(
WHITE,state,p);
192 int hc= RookMobility::countHorizontalAll(
WHITE,state,p);
206 template <
class Opening>
210 using namespace osl::mobility;
213 i<PtypeTraits<BISHOP>::indexLimit;++i){
214 Piece p=state.pieceOf(i);
216 int c= BishopMobility::countAll(
BLACK,state,p);
223 int c= BishopMobility::countAll(
WHITE,state,p);
233 template <
class Opening>
237 using namespace osl::mobility;
240 i<PtypeTraits<LANCE>::indexLimit;++i){
241 Piece p=state.pieceOf(i);
243 int c= LanceMobility::countAll(
BLACK,state,p);
247 int c= LanceMobility::countAll(
WHITE,state,p);
254 template <
class Opening>
inline
258 using namespace osl::mobility;
259 int val=rook_mobility + bishop_mobility + lance_mobility;
260 return val*128/100 * 12;
263 template <
class Opening>
266 const NumEffectState& new_state,
Move last_move)
321 if (captured_base ==
ROOK)
328 else if (captured_base ==
BISHOP)
335 if (captured_base ==
GOLD)
344 else if (captured_base ==
SILVER)
352 if (captured_base ==
LANCE)
357 opening_eval.update(new_state, last_move);
358 endgame_eval.update(new_state, last_move);
359 current_progress.update(new_state, last_move);
360 defense_effect.update(new_state, last_move);
361 minor_piece_bonus.update(new_state, last_move);
363 if (new_state.longEffectChanged<
ROOK>())
364 rook_mobility = calculateMobilityBonusRook(new_state);
365 if (new_state.longEffectChanged<
BISHOP>())
366 bishop_mobility = calculateMobilityBonusBishop(new_state);
367 if (new_state.longEffectChanged<
LANCE>())
368 lance_mobility = calculateMobilityBonusLance(new_state);
370 progress_independent_bonus = calculateMobilityBonus();
371 progress_independent_bonus += calculateAttackRooks(new_state);
372 progress_independent_bonus += calculateSilverPenalty(new_state);
373 progress_independent_bonus += calculateGoldPenalty(new_state);
377 const Square kb = new_state.kingSquare<
BLACK>(), kw = new_state.kingSquare<
WHITE>();
378 BoardMask mask = new_state.changedEffects();
379 mask.set(last_move.
from()); mask.set(last_move.
to());
380 if ((capture_or_drop && new_state.turn() ==
BLACK)
382 attack_bonus[
BLACK] = calculateAttackBonusEach<WHITE>(new_state);
383 if ((capture_or_drop && new_state.turn() ==
WHITE)
385 attack_bonus[
WHITE] = calculateAttackBonusEach<BLACK>(new_state);
387 progress_dependent_bonus = attackBonusScale(attack_bonus[
BLACK],
WHITE);
388 progress_dependent_bonus += attackBonusScale(attack_bonus[
WHITE], BLACK);
389 progress_dependent_bonus += calculatePinBonus(new_state);
390 progress_independent_bonus += calculateKnightCheck(new_state);
391 progress_independent_bonus += calculateRookRankBonus(new_state);
392 progress_independent_bonus += calculateEnterKingBonus<BLACK>(new_state);
393 progress_independent_bonus += calculateEnterKingBonus<WHITE>(new_state);
394 progress_independent_bonus += calculateMiddleKingBonus<BLACK>(new_state);
395 progress_independent_bonus += calculateMiddleKingBonus<WHITE>(new_state);
399 template <
class Opening>
402 const NumEffectState& state)
const
404 const Piece black_king = state.kingPiece<
BLACK>();
405 const Piece white_king = state.kingPiece<
WHITE>();
407 PieceMask white_mask = pin_mask[
WHITE] = state.pin(
WHITE);
408 PieceMask black_mask = pin_mask[
BLACK] = state.pin(
BLACK);
409 while (white_mask.any())
411 const Piece piece = state.pieceOf(white_mask.takeOneBit());
412 bonus -= endgame_eval.valueOf(
413 black_king, white_king,
417 while (black_mask.any())
419 const Piece piece = state.pieceOf(black_mask.takeOneBit());
420 bonus -= endgame_eval.valueOf(
421 black_king, white_king,
425 return bonus * progress16().value() / 16;
428 template <
class Opening>
431 const NumEffectState& state)
const
435 i < PtypeTraits<ROOK>::indexLimit; ++i)
437 const Piece rook = state.pieceOf(i);
439 state.kingPiece(
alt(rook.
owner())).square().canPromote(rook.
owner()))
449 else if (rooks == -2)
455 template <
class Opening>
458 const NumEffectState& state)
const
460 return attackBonusScale(calculateAttackBonusEach<BLACK>(state),
BLACK) +
461 attackBonusScale(calculateAttackBonusEach<WHITE>(state),
WHITE);
464 template <
class Opening>
465 template <osl::Player Attack, osl::Direction Dir>
468 const NumEffectState& state)
const
471 const Square king = state.kingSquare<defense>();
476 const Piece p = state.pieceAt(target);
479 int effect_diff = (state.countEffect(Attack, target) -
481 if ((effect_diff >= 0 && p.
isEmpty()) ||
482 (effect_diff >= 1 && !p.
isEmpty() &&
485 if (Dir ==
UL || Dir ==
U || Dir ==
UR)
487 else if (Dir ==
L || Dir ==
R)
493 if ((effect_diff > 0 &&
494 (target.canPromote<Attack>() ||
495 state.hasEffectByPtype<
GOLD>(Attack,
target) ||
496 state.hasEffectByPtype<
SILVER>(Attack,target) ||
497 state.hasEffectByPtype<
ROOK>(Attack,
target) ||
498 state.hasEffectByPtype<
BISHOP>(Attack,target))) ||
500 can_check_pieces[Attack][Dir] > 0))
512 template <
class Opening>
513 template <osl::Player P>
516 const NumEffectState& state)
const
519 result += calculateAttackBonusOne<P, UL>(state);
520 result += calculateAttackBonusOne<P, U>(state);
521 result += calculateAttackBonusOne<P, UR>(state);
522 result += calculateAttackBonusOne<P, L>(state);
523 result += calculateAttackBonusOne<P, R>(state);
524 result += calculateAttackBonusOne<P, DL>(state);
525 result += calculateAttackBonusOne<P, D>(state);
526 result += calculateAttackBonusOne<P, DR>(state);
530 template <
class Opening>
533 const NumEffectState &state)
const
538 i < PtypeTraits<SILVER>::indexLimit; ++i)
540 const Piece silver = state.pieceOf(i);
551 state.pieceAt(dl).isOnBoardByOwner(silver.
owner()) ||
552 state.hasEffectAt(
alt(silver.
owner()), dl)) &&
554 state.pieceAt(dr).isOnBoardByOwner(silver.
owner()) ||
555 state.hasEffectAt(
alt(silver.
owner()), dr)))
568 template <
class Opening>
571 const NumEffectState &state)
const
576 i < PtypeTraits<GOLD>::indexLimit; ++i)
578 const Piece gold = state.pieceOf(i);
586 if ((state.pieceAt(d).isOnBoardByOwner(gold.
owner()) ||
587 state.hasEffectAt(
alt(gold.
owner()), d)))
600 template <
class Opening>
603 const NumEffectState& state)
const
605 return calculateKnightCheckEach<BLACK>(state) +
606 calculateKnightCheckEach<WHITE>(state);
610 template <
class Opening>
611 template <osl::Player P>
614 const NumEffectState& state)
const
616 const int bonus = (P ==
BLACK ? 1 : -1) *
622 && ! state.pieceAt(up).isEdge())
626 if (! state.pieceAt(ur).isEdge() &&
627 state.pieceAt(ur).isEmpty() &&
629 (state.hasPieceOnStand<
KNIGHT>(P) ||
630 state.hasEffectByPtype<
KNIGHT>(P, ur)))
632 if (state.hasPieceOnStand<
GOLD>(P))
640 if (! state.pieceAt(ul).isEdge() &&
641 state.pieceAt(ul).isEmpty() &&
643 (state.hasPieceOnStand<
KNIGHT>(P) ||
644 state.hasEffectByPtype<
KNIGHT>(P, ul)))
646 if (state.hasPieceOnStand<
GOLD>(P))
656 template <
class Opening>
657 template <osl::Player P>
660 const NumEffectState& state)
const
662 const Square king = state.kingSquare<P>();
664 if ((P ==
BLACK && king.
y() > 4) ||
665 (P ==
WHITE && king.
y() < 6))
671 if ((P ==
BLACK && king.
y() >= 2) ||
672 (P ==
WHITE && king.
y() <= 8))
674 const int y = P ==
BLACK ? king.
y() - 1 : king.
y() + 1;
675 const int min_x =
std::max(1, king.
x() - 1);
676 const int max_x =
std::min(9, king.
x() + 1);
677 bool found_opening =
false;
678 for (
int x = min_x; x <= max_x; ++x)
681 Piece piece = state.pieceAt(pos);
685 found_opening =
true;
686 else if (state.countEffect(P, pos) <=
687 state.countEffect(
alt(P), pos))
694 else if (piece.
owner() == P)
696 if (state.countEffect(P, pos) <
697 state.countEffect(
alt(P), pos))
711 template <
class Opening>
712 template <osl::Player P>
715 const NumEffectState& state)
const
717 const Square king = state.kingSquare<P>();
719 if ((P ==
BLACK && king.
y() >= 6 && major_pieces == 4) ||
720 (P ==
WHITE && king.
y() <= 4 && major_pieces == 0))
727 template<
class Opening>
730 const NumEffectState& state)
const
734 i < PtypeTraits<ROOK>::indexLimit; ++i)
736 const Piece rook = state.pieceOf(i);
738 const int target_y = owner ==
BLACK ? 3 : 7;
739 const int inbetween_y = owner ==
BLACK ? 4 : 6;
746 if (state.hasEffectByPtype<
SILVER>(
751 !state.pieceAt(rank3_pos).isOnBoardByOwner(owner) &&
752 state.countEffect(
alt(owner),
754 state.countEffect(owner,
756 state.countEffect(
alt(owner),
766 state.hasEffectByPiece(rook, rank5.
square())) ||
769 state.hasEffectByPiece(rook, rank4.
square()))) &&
770 !state.hasEffectAt(
alt(owner),
772 state.countEffect(
alt(owner),
781 else if (state.hasEffectByPiece(rook, rank3_pos) &&
782 !state.hasEffectAt(
alt(owner), rank3_pos) &&
783 !state.isPawnMaskSet(owner, rook.
square().
x()))
795 template <
class Opening>
798 Progress16 progress16,
801 PieceValues opening, endgame;
802 const NumEffectState nstate(state);
803 const progress_t progress(nstate);
804 const defense_t defense_effect(nstate);
806 opening_eval_t::setValues(state, opening);
807 endgame_eval_t::setValues(state, endgame);
810 out[i] = composeValue(opening[i] & (~1), endgame[i] & (~1), progress16,
811 progress.progress16(
BLACK),
812 progress.progress16(
WHITE),
813 defense_effect.progress16(
BLACK),
814 defense_effect.progress16(
WHITE),
815 minor_piece_bonus.value(progress16,
816 progress.progress16bonus(
BLACK),
817 progress.progress16bonus(
WHITE)), 0, 0);
821 template <
class Opening>
825 const NumEffectState nstate(state);
826 const progress_t progress(nstate);
827 setValues(state, progress.progress16(),
out);
830 template <
class Opening>
835 debug_info.
eval = value();
836 debug_info.
opening = openingValue();
837 debug_info.
endgame = endgameValue();
838 debug_info.
progress = current_progress.progress16().value();
854 calculateEnterKingBonus<WHITE>(state);
856 calculateMiddleKingBonus<WHITE>(state);
861 debug_info.
pin_bonus = calculatePinBonus(state);
864 minor_piece_bonus.debugInfo(progress16(),
865 progress16bonus(
BLACK),
866 progress16bonus(
WHITE));
879 EffectUtil::findThreat<eval::ProgressEval>(
const NumEffectState& state,