コード例 #1
0
ファイル: movepick.cpp プロジェクト: nmrugg/stockfish.js
void MovePicker::score() {

  static_assert(Type == CAPTURES || Type == QUIETS || Type == EVASIONS, "Wrong type");

  for (auto& m : *this)
      if (Type == CAPTURES)
      {
#ifdef ATOMIC
          if (pos.is_atomic())
              m.value = pos.see<ATOMIC_VARIANT>(m);
          else
#endif
#ifdef RACE
          if (pos.is_race())
              m.value =  PieceValue[pos.variant()][MG][pos.piece_on(to_sq(m))]
                       - Value(200 * relative_rank(BLACK, to_sq(m)))
                       + (*captureHistory)[pos.moved_piece(m)][to_sq(m)][type_of(pos.piece_on(to_sq(m)))] / 8;
          else
#endif
          m.value =  PieceValue[pos.variant()][MG][pos.piece_on(to_sq(m))]
                   + (*captureHistory)[pos.moved_piece(m)][to_sq(m)][type_of(pos.piece_on(to_sq(m)))] / 8;
      }
      else if (Type == QUIETS)
      {
          m.value =  (*mainHistory)[pos.side_to_move()][from_to(m)]
                   + (*continuationHistory[0])[pos.moved_piece(m)][to_sq(m)]
                   + (*continuationHistory[1])[pos.moved_piece(m)][to_sq(m)]
                   + (*continuationHistory[3])[pos.moved_piece(m)][to_sq(m)];
#ifdef ANTI
          if (pos.is_anti() && pos.attackers_to(to_sq(m), pos.pieces() ^ from_sq(m)) & pos.pieces(~pos.side_to_move()))
          {
              m.value += (1 << 28);
              if (!(pos.attackers_to(from_sq(m)) & pos.pieces(~pos.side_to_move())))
                  m.value += (1 << 27);
          }
#endif
      }
      else // Type == EVASIONS
      {
          if (pos.capture(m))
              m.value =  PieceValue[pos.variant()][MG][pos.piece_on(to_sq(m))]
                       - Value(type_of(pos.moved_piece(m)));
          else
              m.value =  (*mainHistory)[pos.side_to_move()][from_to(m)]
                       + (*continuationHistory[0])[pos.moved_piece(m)][to_sq(m)]
                       - (1 << 28);
      }
}
コード例 #2
0
ファイル: movegen.cpp プロジェクト: grefen/challenger
bool move_is_check(const Position& pos, Move move)
{
	Color us = pos.side_to_move();
	Square from = from_sq(move);
	Square to = to_sq(move);
	Square ksq = pos.king_square(~us);

	PieceType pfr = type_of(pos.piece_on(from));
	PieceType pto = type_of(pos.piece_on(to));

	Bitboard pawns = pos.pieces(us, PAWN);
	Bitboard knights = pos.pieces(us, KNIGHT);
	Bitboard cannons = pos.pieces(us, CANNON);
	Bitboard rooks = pos.pieces(us, ROOK);

	Bitboard  occ = pos.pieces();
	Bitboard  occl90 = pos.piecesl90();

	occ ^= from;
	occl90 ^= square_rotate_l90_bb(from);
	if (pto == NO_PIECE_TYPE)
	{
		occ ^= to;
		occl90 ^= square_rotate_l90_bb(to);
	}

	switch (pfr)
	{
	case ROOK:
		rooks ^= from;
		rooks ^= to;
		break;
	case CANNON:
		cannons ^= from;
		cannons ^= to;
		break;
	case KNIGHT:
		knights ^= from;
		knights ^= to;
		break;
	case PAWN:
		pawns ^= from;
		pawns ^= to;
		break;
	default:break;
	}

	if((PseudoAttacks[ROOK][ksq]& cannons) &&(cannon_control_bb(ksq, occ,occl90) & cannons)) return true;
	if((PseudoAttacks[ROOK][ksq]& rooks) && (rook_attacks_bb(ksq,occ,occl90)& rooks) ) return true;
	if( knight_attackers_to_bb(ksq, knights, occ) ) return true;
	if( pos.attacks_from_pawn_nomask(ksq, ~us) & pawns ) return true;

	return false;
}
コード例 #3
0
ファイル: movegen.cpp プロジェクト: Farmii/Stockfish
MoveStack* generate<LEGAL>(const Position& pos, MoveStack* mlist) {

  MoveStack *end, *cur = mlist;
  Bitboard pinned = pos.pinned_pieces();
  Square ksq = pos.king_square(pos.side_to_move());

  end = pos.checkers() ? generate<EVASIONS>(pos, mlist)
                       : generate<NON_EVASIONS>(pos, mlist);
  while (cur != end)
      if (   (pinned || from_sq(cur->move) == ksq || type_of(cur->move) == ENPASSANT)
          && !pos.pl_move_is_legal(cur->move, pinned))
          cur->move = (--end)->move;
      else
          cur++;

  return end;
}
コード例 #4
0
ファイル: movegen.cpp プロジェクト: 0decimal0/Stockfish
ExtMove* generate<LEGAL>(const Position& pos, ExtMove* moveList) {

  Bitboard pinned = pos.pinned_pieces(pos.side_to_move());
  Square ksq = pos.square<KING>(pos.side_to_move());
  ExtMove* cur = moveList;

  moveList = pos.checkers() ? generate<EVASIONS    >(pos, moveList)
                            : generate<NON_EVASIONS>(pos, moveList);
  while (cur != moveList)
      if (   (pinned || from_sq(*cur) == ksq || type_of(*cur) == ENPASSANT)
          && !pos.legal(*cur, pinned))
          *cur = (--moveList)->move;
      else
          ++cur;

  return moveList;
}
コード例 #5
0
ファイル: polybook.c プロジェクト: syzygy1/Cfish
// A PolyGlot book move is encoded as follows:
//
// bit  0- 5: destination square (from 0 to 63)
// bit  6-11: origin square (from 0 to 63)
// bit 12-14: promotion piece (from KNIGHT == 1 to QUEEN == 4)
//
// Castling moves follow "king captures rook" representation. So in case book
// move is a promotion we have to convert to our representation, in all the
// other cases we can directly compare with a Move after having masked out
// the special Move's flags (bit 14-15) that are not supported by PolyGlot.
//
// SF:
// bit  0- 5: destination square (from 0 to 63)
// bit  6-11: origin square (from 0 to 63)
// bit 12-13: promotion piece type - 2 (from KNIGHT-2 to QUEEN-2)
// bit 14-15: special move flag: promotion (1), en passant (2), castling (3)
static Move pg_move_to_sf_move(const Pos *pos, uint16_t pg_move)
{
  Move move = (Move)pg_move;

  int pt = (move >> 12) & 7;
  if (pt)
    return make_promotion(from_sq(move), to_sq(move), pt + 1);

  // Add 'special move' flags and verify it is legal
  ExtMove *m = (pos->st-1)->endMoves;
  ExtMove *end = generate_legal(pos, m);
  for (; m < end; m++)
    if (move == (m->move & (~(3 << 14)))) //  Compare with MoveType (bit 14-15)  masked out
      return m->move;

  return 0;
}
コード例 #6
0
ファイル: movegen.cpp プロジェクト: grefen/challenger
bool move_is_legal(const Position& pos, Move move)
{

	Move m = move;
	assert(is_ok(m));	

	Color us = pos.side_to_move();
	Square from = from_sq(m);
	Square to   = to_sq(m);

	assert(color_of(pos.piece_moved(m)) == us);
	assert(pos.piece_on(pos.king_square(us)) == make_piece(us, KING));

	PieceType pfr = type_of(pos.piece_on(from));
	PieceType pto= type_of(pos.piece_on(to));

	Bitboard pawns   = pos.pieces(~us, PAWN);
	Bitboard knights = pos.pieces(~us, KNIGHT);
	Bitboard cannons = pos.pieces(~us, CANNON);
	Bitboard rooks = pos.pieces(~us, ROOK);

	Bitboard  occ    = pos.pieces();
	Bitboard  occl90 = pos.piecesl90();

	occl90 ^= square_rotate_l90_bb(from);
	occ    ^= from;

	if(pto == NO_PIECE_TYPE)
	{
		occl90 ^= square_rotate_l90_bb(to);
		occ    ^= to;
	}

	Square ksq = pos.king_square(us);
	if(ksq == from)
		ksq = to;

	if (pto != NO_PIECE_TYPE)
	{
		switch(pto)
		{
		case PAWN:
			pawns ^= to;
			break;
		case KNIGHT:
			knights ^= to;
			break;
		case ROOK:
			rooks ^= to;
			break;
		case CANNON:
			cannons ^= to;
			break;
		}
	}



	if((PseudoAttacks[ROOK][ksq]& cannons) &&(cannon_control_bb(ksq, occ,occl90) & cannons)) return false;
	if((PseudoAttacks[ROOK][ksq]& rooks) && (rook_attacks_bb(ksq,occ,occl90)& rooks) ) return false;
	if( knight_attackers_to_bb(ksq, knights, occ) ) return false;
	if( pos.attacks_from_pawn_nomask(ksq, us) & pawns ) return false;

	if((PseudoAttacks[ROOK][ksq]& pos.king_square(~us)) && (rook_attacks_bb(ksq,occ,occl90)& pos.king_square(~us))) return false;//╤таЁ

	return true;
}
コード例 #7
0
ファイル: mate_n_ply.cpp プロジェクト: yaneurao/YaneuraOu
// 利きのある場所への取れない近接王手からの3手詰め
Move Position::weak_mate_n_ply(int ply) const
{
	// 1手詰めであるならこれを返す
	Move m = mate1ply();
	if (m)
		return m;

	// 詰まない
	if (ply <= 1)
		return MOVE_NONE;

	Color us = side_to_move();
	Color them = ~us;
	Bitboard around8 = kingEffect(king_square(them));

	// const剥がし
	Position* This = ((Position*)this);

	StateInfo si;
	StateInfo si2;

	// 近接王手で味方の利きがあり、敵の利きのない場所を探す。
	for (auto m : MoveList<CHECKS>(*this))
	{
		// 近接王手で、この指し手による駒の移動先に敵の駒がない。
		Square to = to_sq(m);
		if ((around8 & to)

#ifndef LONG_EFFECT_LIBRARY
			// toに利きがあるかどうか。mが移動の指し手の場合、mの元の利きを取り除く必要がある。
			&& (is_drop(m) ? effected_to(us, to) : (attackers_to(us, to, pieces() ^ from_sq(m)) ^ from_sq(m)))

			// 敵玉の利きは必ずtoにあるのでそれを除いた利きがあるかどうか。
			&& (attackers_to(them,to,pieces()) ^ king_square(them))
#else
			&& (is_drop(m) ? effected_to(us, to) :
					board_effect[us].effect(to) >= 2 ||
					(long_effect.directions_of(us, from_sq(m)) & Effect8::directions_of(from_sq(m), to)) != 0)

			// 敵玉の利きがあるので2つ以上なければそれで良い。
			&& (board_effect[them].effect(to) <= 1)
#endif
			)
		{
			if (!legal(m))
				continue;

			ASSERT_LV3(gives_check(m));

			This->do_move(m,si,true);

			ASSERT_LV3(in_check());

			// この局面ですべてのevasionを試す
			for (auto m2 : MoveList<EVASIONS>(*this))
			{
				if (!legal(m2))
					continue;

				// この指し手で逆王手になるなら、不詰めとして扱う
				if (gives_check(m2))
					goto NEXT_CHECK;

				This->do_move(m2, si2, false);

				ASSERT_LV3(!in_check());

				if (!weak_mate_n_ply(ply-2))
				{
					// 詰んでないので、m2で詰みを逃れている。
					This->undo_move(m2);
					goto NEXT_CHECK;
				}

				This->undo_move(m2);
			}

			// すべて詰んだ
			This->undo_move(m);

			// mによって3手で詰む。
			return m;

		NEXT_CHECK:;
			This->undo_move(m);
		}
	}
	return MOVE_NONE;
}