Ver código fonte

trying out new search algorithm

nicolaswinkler 7 anos atrás
pai
commit
6812c0bc5c
5 arquivos alterados com 199 adições e 11 exclusões
  1. 10 10
      src/Board.cpp
  2. 1 1
      src/Minimax.h
  3. 1 0
      src/MoveGeneration.h
  4. 185 0
      src/Search.h
  5. 2 0
      src/main.cpp

+ 10 - 10
src/Board.cpp

@@ -53,16 +53,6 @@ bool Board::tryToMove(Bitboard start, Bitboard end, Bitboard& b)
 }
 
 
-void Board::removeAt(Index i)
-{
-    Bitboard mask = ~Bitboard::fromIndex(i);
-    for (Bitboard& b : whites)
-        b &= mask;
-    for (Bitboard& b : blacks)
-        b &= mask;
-}
-
-
 void Board::setBoard(const std::string& fenPosition)
 {
     int row = 7, column = 0;
@@ -203,6 +193,16 @@ void Board::move(const Move& move)
 }
 
 
+void Board::removeAt(Index i)
+{
+    Bitboard mask = ~Bitboard::fromIndex(i);
+    for (Bitboard& b : whites)
+        b &= mask;
+    for (Bitboard& b : blacks)
+        b &= mask;
+}
+
+
 Bitboard Board::getWhites(void) const
 {
     return whites[0] | whites[1] | whites[2] | whites[3] | whites[4] | whites[5];

+ 1 - 1
src/Minimax.h

@@ -2,7 +2,7 @@
 #define CHESSY_MINIMAX_H
 
 #include "MoveGeneration.h"
-
+#include "Search.h"
 
 namespace chessy
 {

+ 1 - 0
src/MoveGeneration.h

@@ -30,6 +30,7 @@ namespace chessy
 }
 
 
+
 class chessy::PositionSet
 {
     Bitboard bitboard;

+ 185 - 0
src/Search.h

@@ -0,0 +1,185 @@
+#ifndef CHESSY_SEARCH_H
+#define CHESSY_SEARCH_H
+
+#include "ChessGame.h"
+
+namespace chessy
+{
+    template<typename T>
+    class Search;
+
+    class MinimaxN;
+}
+
+
+template<typename T>
+class chessy::Search
+{
+    T& handler;
+    ChessGame& game;
+public:
+    inline Search(T& handler, ChessGame& game) :
+        game{ game }, handler{ handler } {}
+
+
+    template<typename... Args>
+    inline void iterateAll(Args&&... args);
+private:
+};
+
+
+class chessy::MinimaxN
+{
+public:
+    bool operator () (int a, int b) {
+        return true;
+    }
+};
+
+
+inline void aga() {
+    chessy::ChessGame cg;
+    chessy::MinimaxN mm;
+    chessy::Search<chessy::MinimaxN> search = { mm, cg };
+    search.iterateAll(5, 8ULL);
+}
+
+
+template<typename... Args>
+inline void chessy::Search::iterateAll(Args&&... args)
+{
+    Board& board = game.getBoard();
+    Bitboard friends;
+    Bitboard enemies;
+    if (side == WHITE_SIDE) {
+        friends = board.getWhites();
+        enemies = board.getBlacks();
+    }
+    else {
+        friends = board.getBlacks();
+        enemies = board.getWhites();
+    }
+
+    const Board temp = board;
+    PawnPushGenerator<side> mg{ game };
+    for (Move push : mg) {
+        Bitboard& pawns = board.getPawns<side>();
+        Bitboard pTemp = pawns;
+        pawns.applyMove(push);
+        BestMove m = minimax<otherSide(side)>(depth - 1);
+        m.move = push;
+        bestMove.overwriteIfBetter(m);
+        pawns = pTemp;
+    }
+
+    PawnDoublePushGenerator<side> dp{ game };
+    for (Move push : dp) {
+        Bitboard& pawns = board.getPawns<side>();
+        Bitboard pTemp = pawns;
+        pawns.applyMove(push);
+        BestMove m = minimax<otherSide(side)>(depth - 1);
+        m.move = push;
+        bestMove.overwriteIfBetter(m);
+        pawns = pTemp;
+    }
+
+    PawnCaptureGenerator<side, LEFT> pl{ game };
+    for (Move capture : pl) {
+        Bitboard& pawns = board.getPawns<side>();
+        board.removeAt(capture.destination);
+        pawns.applyMove(capture);
+        BestMove m = minimax<otherSide(side)>(depth - 1);
+        m.move = capture;
+        bestMove.overwriteIfBetter(m);
+        board = temp;
+    }
+    
+    PawnCaptureGenerator<side, RIGHT> pr{ game };
+    for (Move capture : pr) {
+        Bitboard& pawns = board.getPawns<side>();
+        board.removeAt(capture.destination);
+        pawns.applyMove(capture);
+        BestMove m = minimax<otherSide(side)>(depth - 1);
+        m.move = capture;
+        bestMove.overwriteIfBetter(m);
+        board = temp;
+    }
+
+
+    Bitboard& ns = board.getKnights<side>();
+    PositionSet knights { ns };
+    for (auto knight : knights) {
+        for (auto pos : KnightMoveGenerator{ knight, friends }) {
+            Move move = { knight, pos };
+            board.removeAt(move.destination);
+            ns.applyMove(move);
+            BestMove m = minimax<otherSide(side)>(depth - 1);
+            m.move = move;
+            bestMove.overwriteIfBetter(m);
+            board = temp;
+        }
+    }
+
+    Bitboard& bs = board.getBishops<side>();
+    PositionSet bishops { bs }; 
+    for (auto bishop : bishops) {
+        for (auto pos : PrimitiveBishopMoveGenerator{ bishop, enemies, friends }) {
+            Move move = { bishop, pos };
+            board.removeAt(move.destination);
+            bs.applyMove(move);
+            BestMove m = minimax<otherSide(side)>(depth - 1);
+            m.move = move;
+            bestMove.overwriteIfBetter(m);
+            board = temp;
+        }
+    }
+
+    Bitboard& rs = board.getRooks<side>();
+    PositionSet rooks { rs }; 
+    for (auto rook : rooks) {
+        for (auto pos : PrimitiveRookMoveGenerator{ rook, enemies, friends }) {
+            Move move = { rook, pos };
+            board.removeAt(move.destination);
+            rs.applyMove(move);
+            BestMove m = minimax<otherSide(side)>(depth - 1);
+            m.move = move;
+            bestMove.overwriteIfBetter(m);
+            board = temp;
+        }
+    }
+
+    Bitboard& qs = board.getQueens<side>();
+    PositionSet queens { qs };
+    for (auto queen : queens) {
+        for (auto pos : PrimitiveQueenMoveGenerator{ queen, enemies, friends }) {
+            Move move = { queen, pos };
+            board.removeAt(move.destination);
+            qs.applyMove(move);
+            BestMove m = minimax<otherSide(side)>(depth - 1);
+            m.move = move;
+            bestMove.overwriteIfBetter(m);
+            board = temp;
+        }
+    }
+
+    Bitboard& king = board.getKing<side>();
+    Index kingIndex = king.getLeastSignificantBit();
+    for (auto pos : KingMoveGenerator{ king, friends }) {
+        Move move = { kingIndex, pos };
+        board.removeAt(pos);
+        king.applyMove(move);
+        BestMove m = minimax<otherSide(side)>(depth - 1);
+        m.move = move;
+        //if (depth >= 3)
+        //    std::cout << m.move.asString() << " " << bestMove.value << " -> " << m.value << std::endl;
+        bestMove.overwriteIfBetter(m);
+        board = temp;
+    }
+    float v = evaluate<side>();
+    bestMove.value *= 0.9f;
+    bestMove.value += v * 0.2f;
+    return -bestMove;
+}
+
+
+#endif // CHESSY_SEARCH_H

+ 2 - 0
src/main.cpp

@@ -8,6 +8,8 @@ using namespace chessy;
 
 auto main(int argc, char** argv) -> int
 {
+    aga();
+
     UciParser uciParser;
     uciParser.parse(cin, cout);
     return 0;