newProgress.h
Go to the documentation of this file.
00001 /* newProgress.h */
00002 #ifndef PROGRESS_EXPERIMENTAL_NEW_PROGRESS_H
00003 #define PROGRESS_EXPERIMENTAL_NEW_PROGRESS_H
00004 
00005 #include "osl/state/numEffectState.h"
00006 #include "osl/progress/progress16.h"
00007 #include "osl/eval/ml/midgame.h"
00008 #include "osl/centering5x3.h"
00009 #include "osl/misc/carray.h"
00010 namespace osl
00011 {
00012   namespace progress
00013   {
00014     namespace ml
00015     {
00016       struct NewProgressDebugInfo
00017       {
00018         enum Feature
00019         {
00020           ATTACK_5X3,
00021           DEFENSE_5X3,
00022           ATTACK5X5,
00023           STAND,
00024           EFFECT5X5,
00025           KING_RELATIVE_ATTACK,
00026           KING_RELATIVE_DEFENSE,
00027           NON_PAWN_ATTACKED_PAIR,
00028           FEATURE_LIMIT
00029         };
00030         CArray<int, FEATURE_LIMIT> black_values;
00031         CArray<int, FEATURE_LIMIT> white_values;
00032       };
00033 
00034       struct NewProgressData
00035       {
00036         CArray<MultiInt,2> non_pawn_ptype_attacked_pair_eval;
00037         MultiInt promotion37_eval;
00038         CArray<int, 2> progresses, attack5x5_progresses, stand_progresses,
00039           effect_progresses, defenses;
00040         CArray<int, 2> rook, bishop, gold, silver, promoted,
00041           king_relative_attack, king_relative_defense, non_pawn_ptype_attacked_pair;
00042         int pawn_facing, promotion37, piecestand7;
00043       };
00044       class NewProgress : private NewProgressData
00045       {
00046       public:
00047         enum { ProgressScale = 2 };
00048       private:
00049         static bool initialized_flag;
00050         static CArray<int, Piece::SIZE> stand_weight;
00051         static CArray<int, 1125> attack5x5_weight;
00052         static CArray<int, 5625> attack5x5_x_weight;
00053         static CArray<int, 10125> attack5x5_y_weight;
00054         static CArray<int, 75> effectstate_weight;
00055         static CArray<int, 81*15*10> attack_relative;
00056         static CArray<int, 81*15*10> defense_relative;
00057         static CArray<int, 4284> king_relative_weight;
00058         static CArray<int, 262144> attacked_ptype_pair_weight;
00059         static CArray<int, 10> pawn_facing_weight;
00060         static CArray<int, 16> promotion37_weight;
00061         static CArray<int, 56> piecestand7_weight;
00062         static int max_progress;
00063         void updatePieceKingRelativeBonus(const NumEffectState &state);
00064         void updateNonPawnAttackedPtypePair(const NumEffectState& state);
00065         template <Player Owner>
00066         void updateNonPawnAttackedPtypePairOne(const NumEffectState& state);
00067         void updatePawnFacing(const NumEffectState& state);
00068         template <Player Attack>        
00069         void promotion37One(const NumEffectState& state, int rank);
00070         void updatePromotion37(const NumEffectState& state);
00071         void updatePieceStand7(const NumEffectState& state);
00072         template <Player P>
00073         static void progressOne(const NumEffectState &state,
00074                                 int &attack, int &defense);
00075         template <Player P>
00076         void updateAttack5x5PiecesAndState(const NumEffectState &state);
00077         template <Player P>
00078         void updateAttack5x5Pieces(PieceMask, const NumEffectState&);
00079         template <Player P>
00080         int attack5x5Value(const NumEffectState &state) const;
00081         template <Player P>
00082         static int index(Square king, Square target)
00083         {
00084           const int x_diff = std::abs(king.x() - target.x()); // [0, 4]
00085           const int y_diff = (P == BLACK ? king.y() - target.y() :
00086                               target.y() - king.y()) + 2; // [-2, 2] + 2
00087           return x_diff * 5 + y_diff;
00088         }
00089         template <Player P>
00090         static int indexX(Square king, Square target)
00091         {
00092           int target_x = (king.x() > 5 ? 10 - king.x() : king.x()); // [1, 5]
00093           int x_diff = king.x() - target.x(); // [-4, 4]
00094           if (P == BLACK && king.x() >= 6)
00095           {
00096             x_diff = -x_diff;
00097           }
00098           else if (P == WHITE && king.x() >= 5)
00099           {
00100             x_diff = -x_diff;
00101           }
00102           const int y_diff = (P == BLACK ? king.y() - target.y() :
00103                               target.y() - king.y()) + 2; // [-2, 2] + 2
00104           return ((x_diff + 4) * 5 + y_diff) * 5 + target_x - 1;
00105         }
00106         template <Player P>
00107         static int indexY(Square king, Square target)
00108         {
00109           const int x_diff = std::abs(king.x() - target.x()); // [0, 4]
00110           const int y_diff = (P == BLACK ? king.y() - target.y() :
00111                               target.y() - king.y()) + 2; // [-2, 2] + 2
00112           const int king_y = (P == BLACK ? king.y() : 10 - king.y()); // [1, 9]
00113           return (x_diff * 5 + y_diff) * 9 + king_y - 1;
00114         }
00115         static int index5x5(int rook, int bishop, int gold, int silver,
00116                             int promoted)
00117         {
00118           assert(0 <= promoted && promoted <= 4);
00119           return promoted + 5 * (silver + 5 * (gold + 5 * (bishop + 3 * rook)));
00120         }
00121         static int index5x5x(int rook, int bishop, int gold, int silver,
00122                              int promoted, int king_x)
00123         {
00124           assert(0 <= promoted && promoted <= 4);
00125           return king_x - 1 +
00126             5 * (promoted + 5 * (silver + 5 * (gold + 5 * (bishop + 3 * rook))));
00127         }
00128         static int index5x5y(int rook, int bishop, int gold, int silver,
00129                              int promoted, int king_y)
00130         {
00131           assert(0 <= promoted && promoted <= 4);
00132           return king_y - 1 +
00133             9 * (promoted + 5 * (silver + 5 * (gold + 5 * (bishop + 3 * rook))));
00134         }
00135         template <Player P>
00136         static int indexPerEffect(Square king, Square target,
00137                                   int count)
00138         {
00139           const int x_diff = std::abs(king.x() - target.x()); // [0, 4]
00140           const int y_diff = (P == BLACK ? king.y() - target.y() :
00141                               target.y() - king.y()) + 2; // [-2, 2] + 2
00142           return x_diff * 5 + y_diff + std::min(8, count) * 25;
00143         }
00144 
00145         template <Player P>
00146         static int indexPerEffectY(Square king, Square target,
00147                                    int count)
00148         {
00149           const int king_y = (P == BLACK ? king.y() : 10 - king.y());
00150           const int x_diff = std::abs(king.x() - target.x()); // [0, 4]
00151           const int y_diff = (P == BLACK ? king.y() - target.y() :
00152                               target.y() - king.y()) + 2; // [-2, 2] + 2
00153           return king_y - 1 + 9 * (x_diff * 5 + y_diff + std::min(8, count) * 25);
00154         }
00155         template <Player P>
00156         static int indexPerEffectX(Square king, Square target,
00157                                    int count)
00158         {
00159           const int king_x = (king.x() > 5 ? 10 - king.x() : king.x());
00160           int x_diff = king.x() - target.x(); // [-4, 4]
00161           if ((P == BLACK && (king.x() > 5)) ||
00162               (P == WHITE && (king.x() >= 5)))
00163             x_diff = -x_diff;
00164           const int y_diff = (P == BLACK ? king.y() - target.y() :
00165                               target.y() - king.y()) + 2; // [-2, 2] + 2
00166           return king_x - 1 + 5 * (x_diff + 4 +
00167                                    9 * (y_diff + 5 *  std::min(8, count)));
00168         }
00169         template <Player P>
00170         static int indexRelative(const Square king,
00171                                  const Ptype ptype, const Square pos)
00172         {
00173           const int x = std::abs(pos.x() - king.x());
00174           const int y = (king.y() - pos.y()) *
00175             (P == osl::BLACK ? 1 : -1) + 8;
00176           return (ptype - osl::PTYPE_PIECE_MIN) * 17 * 9 + (x * 17 + y);
00177         }
00178         static int indexRelative(const Player player, const Square king,
00179                                  const Piece piece)
00180         {
00181           if (player == BLACK)
00182           {
00183             return indexRelative<BLACK>(king, piece.ptype(),
00184                                         piece.square());
00185           }
00186           else
00187           {
00188             return indexRelative<WHITE>(king, piece.ptype(),
00189                                         piece.square());
00190           }
00191         }
00192       public:
00193         NewProgress(const NumEffectState &state);
00194         int progress() const
00195         {
00196           return
00197             std::max(std::min(progresses[0] + progresses[1] +
00198                               attack5x5_progresses[0] +
00199                               attack5x5_progresses[1] +
00200                               stand_progresses[0] + stand_progresses[1] +
00201                               effect_progresses[0] + effect_progresses[1] +
00202                               defenses[0] + defenses[1] +
00203                               king_relative_attack[0] +
00204                               king_relative_attack[1] +
00205                               king_relative_defense[0] +
00206                               king_relative_defense[1] +
00207                               non_pawn_ptype_attacked_pair[0] +
00208                               non_pawn_ptype_attacked_pair[1] +
00209                               pawn_facing + promotion37 + piecestand7,
00210                               max_progress-ProgressScale), 0) / ProgressScale;
00211         }
00212         static int maxProgress() { return max_progress / ProgressScale; }
00213         template<Player P>
00214         void updateSub(const NumEffectState &new_state, Move last_move);
00215         void update(const NumEffectState &new_state, Move last_move){
00216           if(new_state.turn()==BLACK)
00217             updateSub<WHITE>(new_state,last_move);
00218           else
00219             updateSub<BLACK>(new_state,last_move);
00220         }
00221         NewProgressDebugInfo debugInfo() const;
00222       private:
00223         template<Player P>
00224         void updateMain(const NumEffectState &new_state, Move last_move);
00225       public:
00226         const Progress16 progress16() const
00227         {
00228           return Progress16(16 * progress() / maxProgress());
00229         }
00230         const Progress16 progress16(Player p) const
00231         {
00232           assert(maxProgress() > 0);
00233           return Progress16(
00234             16 * std::max(
00235               std::min(progresses[playerToIndex(alt(p))] +
00236                        attack5x5_progresses[playerToIndex(alt(p))] +
00237                        stand_progresses[playerToIndex(alt(p))] +
00238                        effect_progresses[playerToIndex(alt(p))] +
00239                        defenses[playerToIndex(alt(p))] +
00240                        king_relative_attack[playerToIndex(alt(p))] +
00241                        king_relative_defense[playerToIndex(p)] +
00242                        non_pawn_ptype_attacked_pair[p],
00243                        max_progress-ProgressScale), 0)
00244             / ProgressScale / maxProgress());
00245         }
00246         // p == attack player, alt(p) == king owner
00247         const Progress16 progressAttack(Player p) const
00248         {
00249           assert(maxProgress() > 0);
00250           return Progress16(
00251             8 * std::max(
00252               std::min(progresses[alt(p)] +
00253                        attack5x5_progresses[alt(p)] +
00254                        stand_progresses[alt(p)] +
00255                        effect_progresses[alt(p)] +
00256                        king_relative_attack[alt(p)],
00257                        max_progress-ProgressScale), -max_progress+ProgressScale)
00258             / ProgressScale / maxProgress() + 8);
00259         }
00260         // p == king owner (defense player)
00261         const Progress16 progressDefense(Player p) const
00262         {
00263           assert(maxProgress() > 0);
00264           return Progress16(
00265             8 * std::max(
00266               std::min(defenses[alt(p)] +
00267                        king_relative_defense[p] +
00268                        non_pawn_ptype_attacked_pair[p],
00269                        max_progress-ProgressScale),
00270               -max_progress + ProgressScale)
00271             / ProgressScale / maxProgress() + 8);
00272         }
00273         static bool initialized()
00274         {
00275           return initialized_flag;
00276         }
00277         static bool setUp(const char *filename);
00278         static bool setUp();
00279         static std::string defaultFilename();
00280         const NewProgressData rawData() const { return *this; }
00281       };
00282       bool operator==(const NewProgressData& l, const NewProgressData& r);
00283       inline bool operator==(const NewProgress& l, const NewProgress& r) 
00284       {
00285         return l.rawData() == r.rawData();
00286       }
00287     }
00288   }
00289 }
00290 
00291 #endif // PROGRESS_EXPERIMENTAL_NEW_PROGRESS_H
00292 // ;;; Local Variables:
00293 // ;;; mode:c++
00294 // ;;; c-basic-offset:2
00295 // ;;; End:
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines