]> git.sesse.net Git - stockfish/blobdiff - src/pawns.cpp
Introduce PawnsQtyTable[] to refine pawn's drawish calculation
[stockfish] / src / pawns.cpp
index 8f4232d7580a49e7008706abf55e14cbb360e4ac..65bb3dbaa38d1dcc9224639f6d0c5bf4ae860313 100644 (file)
@@ -70,6 +70,13 @@ namespace {
     S(34,68), S(83,166), S(0, 0), S( 0, 0)
   };
 
+  // UnpairedPawnsTable[] gives a score according to the number
+  // of panws that do not have an enemy pawn in front of them.
+  const int UnpairedPawnsTable[16] = { 32, 48, 64, 80, 96, 112, 128, 128, 128 };
+
+  // PawnsQtyTable[] gives a score according to the number of panws
+  const int PawnsQtyTable[16] = { 16, 16, 16, 16, 16, 16, 16, 16, 16 };
+
   // Pawn storm tables for positions with opposite castling
   const int QStormTable[64] = {
     0,  0,  0,  0, 0, 0, 0, 0,
@@ -183,10 +190,11 @@ Score PawnInfoTable::evaluate_pawns(const Position& pos, Bitboard ourPawns,
   Square s;
   File f;
   Rank r;
-  bool passed, isolated, doubled, chain, backward, candidate;
+  bool passed, isolated, doubled, opposed, chain, backward, candidate;
   int bonus;
   Score value = make_score(0, 0);
   const Square* ptr = pos.piece_list_begin(Us, PAWN);
+  int unpairedPawnsNum = pos.piece_count(Us, PAWN);
 
   // Initialize pawn storm scores by giving bonuses for open files
   for (f = FILE_A; f <= FILE_H; f++)
@@ -206,9 +214,14 @@ Score PawnInfoTable::evaluate_pawns(const Position& pos, Bitboard ourPawns,
       assert(pos.piece_on(s) == piece_of_color_and_type(Us, PAWN));
 
       // Passed, isolated or doubled pawn?
-      passed   = Position::pawn_is_passed(theirPawns, Us, s);
-      isolated = Position::pawn_is_isolated(ourPawns, s);
-      doubled  = Position::pawn_is_doubled(ourPawns, Us, s);
+      passed   = !(theirPawns & passed_pawn_mask(Us, s));
+      isolated = !(ourPawns & neighboring_files_bb(s));
+      doubled  = ourPawns & squares_behind(Us, s);
+      opposed  = theirPawns & squares_in_front_of(Us, s);
+
+      // Decrease number of unpaired pawns
+      if (opposed)
+          unpairedPawnsNum--;
 
       // We calculate kingside and queenside pawn storm
       // scores for both colors. These are used when evaluating
@@ -299,7 +312,7 @@ Score PawnInfoTable::evaluate_pawns(const Position& pos, Bitboard ourPawns,
 
       // Test for candidate passed pawn
       candidate =   !passed
-                 && !(theirPawns & file_bb(f))
+                 && !opposed
                  && (  count_1s_max_15(neighboring_files_bb(f) & (behind_bb(Us, r) | rank_bb(r)) & ourPawns)
                      - count_1s_max_15(neighboring_files_bb(f) & in_front_bb(Us, r)              & theirPawns)
                      >= 0);
@@ -336,6 +349,9 @@ Score PawnInfoTable::evaluate_pawns(const Position& pos, Bitboard ourPawns,
           value += CandidateBonus[relative_rank(Us, s)];
   }
 
+  // Calculate a scale factor to be used to evaluate if position is drawish
+  pi->factor[Us] = UnpairedPawnsTable[unpairedPawnsNum] * PawnsQtyTable[pos.piece_count(Us, PAWN)] / 16;
+
   return value;
 }