(self, move)
Updates the position with the given move and puts it onto a stack.

        Null moves just increment the move counters, switch turns and forfeit
        en passant capturing.

        No validation is performed. For performance moves are assumed to be at
        least pseudo legal. Otherwise there is no guarantee that the previous
        board state can be restored. To check it yourself you can use:

        >>> move in board.pseudo_legal_moves
        True
Updates the position with the given move and puts it onto a stack.
Updates the position with the given move and puts it onto a stack .
def push(self, move):
        """
        Updates the position with the given move and puts it onto a stack.

        Null moves just increment the move counters, switch turns and forfeit
        en passant capturing.

        No validation is performed. For performance moves are assumed to be at
        least pseudo legal. Otherwise there is no guarantee that the previous
        board state can be restored. To check it yourself you can use:

        >>> move in board.pseudo_legal_moves
        True
        """
        # Increment ply.
        if self.turn == BLACK:
            self.ply += 1

        # Remember game state.
        captured_piece = self.piece_type_at(move.to_square) if move else NONE
        self.half_move_stack.append(self.half_moves)
        self.castling_right_stack.append(self.castling_rights)
        self.captured_piece_stack.append(captured_piece)
        self.ep_square_stack.append(self.ep_square)
        self.move_stack.append(move)

        # Update half move counter.
        piece_type = self.piece_type_at(move.from_square)
        if piece_type == PAWN or captured_piece:
            self.half_moves = 0
        else:
            self.half_moves += 1

        # On a null move simply swap turns.
        if not move:
            self.turn ^= 1
            self.ep_square = 0
            return

        # Promotion.
        if move.promotion:
            piece_type = move.promotion

        # Remove piece from target square.
        self.remove_piece_at(move.from_square)

        # Handle special pawn moves.
        self.ep_square = 0
        if piece_type == PAWN:
            diff = abs(move.to_square - move.from_square)

            # Remove pawns captured en-passant.
            if (diff == 7 or diff == 9) and not self.occupied & BB_SQUARES[move.to_square]:
                if self.turn == WHITE:
                    self.remove_piece_at(move.to_square - 8)
                else:
                    self.remove_piece_at(move.to_square + 8)

            # Set en-passant square.
            if diff == 16:
                if self.turn == WHITE:
                    self.ep_square = move.to_square - 8
                else:
                    self.ep_square = move.to_square + 8

        # Castling rights.
        if move.from_square == E1:
            self.castling_rights &= ~CASTLING_WHITE
        elif move.from_square == E8:
            self.castling_rights &= ~CASTLING_BLACK
        elif move.from_square == A1 or move.to_square == A1:
            self.castling_rights &= ~CASTLING_WHITE_QUEENSIDE
        elif move.from_square == A8 or move.to_square == A8:
            self.castling_rights &= ~CASTLING_BLACK_QUEENSIDE
        elif move.from_square == H1 or move.to_square == H1:
            self.castling_rights &= ~CASTLING_WHITE_KINGSIDE
        elif move.from_square == H8 or move.to_square == H8:
            self.castling_rights &= ~CASTLING_BLACK_KINGSIDE

        # Castling.
        if piece_type == KING:
            if move.from_square == E1 and move.to_square == G1:
                self.set_piece_at(F1, Piece(ROOK, WHITE))
                self.remove_piece_at(H1)
            elif move.from_square == E1 and move.to_square == C1:
                self.set_piece_at(D1, Piece(ROOK, WHITE))
                self.remove_piece_at(A1)
            elif move.from_square == E8 and move.to_square == G8:
                self.set_piece_at(F8, Piece(ROOK, BLACK))
                self.remove_piece_at(H8)
            elif move.from_square == E8 and move.to_square == C8:
                self.set_piece_at(D8, Piece(ROOK, BLACK))
                self.remove_piece_at(A8)

        # Put piece on target square.
        self.set_piece_at(move.to_square, Piece(piece_type, self.turn))

        # Swap turn.
        self.turn ^= 1
def push ( self , move ) : # Increment ply. if self . turn == BLACK : self . ply += 1 # Remember game state. captured_piece = self . piece_type_at ( move . to_square ) if move else NONE self . half_move_stack . append ( self . half_moves ) self . castling_right_stack . append ( self . castling_rights ) self . captured_piece_stack . append ( captured_piece ) self . ep_square_stack . append ( self . ep_square ) self . move_stack . append ( move ) # Update half move counter. piece_type = self . piece_type_at ( move . from_square ) if piece_type == PAWN or captured_piece : self . half_moves = 0 else : self . half_moves += 1 # On a null move simply swap turns. if not move : self . turn ^= 1 self . ep_square = 0 return # Promotion. if move . promotion : piece_type = move . promotion # Remove piece from target square. self . remove_piece_at ( move . from_square ) # Handle special pawn moves. self . ep_square = 0 if piece_type == PAWN : diff = abs ( move . to_square - move . from_square ) # Remove pawns captured en-passant. if ( diff == 7 or diff == 9 ) and not self . occupied & BB_SQUARES [ move . to_square ] : if self . turn == WHITE : self . remove_piece_at ( move . to_square - 8 ) else : self . remove_piece_at ( move . to_square + 8 ) # Set en-passant square. if diff == 16 : if self . turn == WHITE : self . ep_square = move . to_square - 8 else : self . ep_square = move . to_square + 8 # Castling rights. if move . from_square == E1 : self . castling_rights &= ~ CASTLING_WHITE elif move . from_square == E8 : self . castling_rights &= ~ CASTLING_BLACK elif move . from_square == A1 or move . to_square == A1 : self . castling_rights &= ~ CASTLING_WHITE_QUEENSIDE elif move . from_square == A8 or move . to_square == A8 : self . castling_rights &= ~ CASTLING_BLACK_QUEENSIDE elif move . from_square == H1 or move . to_square == H1 : self . castling_rights &= ~ CASTLING_WHITE_KINGSIDE elif move . from_square == H8 or move . to_square == H8 : self . castling_rights &= ~ CASTLING_BLACK_KINGSIDE # Castling. if piece_type == KING : if move . from_square == E1 and move . to_square == G1 : self . set_piece_at ( F1 , Piece ( ROOK , WHITE ) ) self . remove_piece_at ( H1 ) elif move . from_square == E1 and move . to_square == C1 : self . set_piece_at ( D1 , Piece ( ROOK , WHITE ) ) self . remove_piece_at ( A1 ) elif move . from_square == E8 and move . to_square == G8 : self . set_piece_at ( F8 , Piece ( ROOK , BLACK ) ) self . remove_piece_at ( H8 ) elif move . from_square == E8 and move . to_square == C8 : self . set_piece_at ( D8 , Piece ( ROOK , BLACK ) ) self . remove_piece_at ( A8 ) # Put piece on target square. self . set_piece_at ( move . to_square , Piece ( piece_type , self . turn ) ) # Swap turn. self . turn ^= 1