I would be interested in the correctness of this minimax execution, I have a problem with the fact that if, for example, I throw out the opponent’s queen in the last dive, then this move is evaluated with a large number of points, but it was preceded by meaningless moves and it seems to me that the min-max does not proceed correctly.
void CGame::minimaxAlphaBeta(int depth, int typeOponent)
{
Color nextMove = Color::WHITE;
while(!isFinished(nextMove))
{
if(nextMove == m_Player)
{
playerMakeMove();
}
else
{
map<int, pair<CPosition, CPosition>, greater<int>> tempBestMoves;
minimaxAlphaBetaAlg(*this, depth, INT_MIN, INT_MAX, true, m_Computer, depth, tempBestMoves);
auto& firstMove = *tempBestMoves.begin();
makeMove(firstMove.second.first, firstMove.second.second, m_Computer, true);
}
nextMove = (nextMove == Color::WHITE) ? Color::BLACK : Color::WHITE;
}
}
int CGame::minimaxAlphaBetaAlg(CGame &game, int depth, int alpha, int beta, bool isMaximizingComputer, Color playerColor, int originalDepth, map<int, pair<CPosition, CPosition>, greater<int>>& bestMoves)
{
if(game.isFinished(playerColor) || depth == 0)
{
int val = game.evaluateBoard(playerColor, originalDepth, depth);
return val;
}
int bestEval = isMaximizingComputer ? INT_MIN : INT_MAX;
auto& playableMoves = (isMaximizingComputer ?
((m_Computer == Color::WHITE) ? game.m_WhitePlayable : game.m_BlackPlayable) :
((m_Player == Color::WHITE) ? game.m_WhitePlayable : game.m_BlackPlayable));
for (auto& [from, to] : playableMoves)
{
CGame gameCopy = game;
gameCopy.makeMove(from, to, isMaximizingComputer ? m_Computer : m_Player, true);
(playerColor == m_Computer) ? playerColor = game.m_Player : playerColor = game.m_Computer;
int eval = minimaxAlphaBetaAlg(gameCopy, depth - 1, alpha, beta, !isMaximizingComputer, playerColor, originalDepth, bestMoves);
if(isMaximizingComputer)
{
if(eval > bestEval)
{
bestEval = eval;
}
alpha = max(alpha, bestEval);
}
else
{
bestEval = min(bestEval, eval);
beta = min(beta, bestEval);
}
if(beta <= alpha)
break;
if(depth == originalDepth && isMaximizingComputer)
{
cout << bestEval << endl;
bestMoves[bestEval] = make_pair(from, to);
}
}
return bestEval;
}
Eval function
int CGame::evaluateBoard(Color color, int maxDepth, int depth)
{
int eval = 0;
for(long int i = 0; i < m_Board.getSize(); i++)
{
for (long int j = 0; j < m_Board.getSize(); j++)
{
if(m_Board[i][j].getType() == Type::QUEEN)
{
if(m_Board[i][j].getColor() == color)
eval += 120;
else
eval -= 120;
}
else if(m_Board[i][j].getType() == Type::ROOK)
{
if(m_Board[i][j].getColor() == color)
eval += 50;
else
eval -= 50;
}
else if(m_Board[i][j].getType() == Type::KNIGHT)
{
if(m_Board[i][j].getColor() == color)
eval += 20;
else
eval -= 20;
}
else if(m_Board[i][j].getType() == Type::BISHOP)
{
if(m_Board[i][j].getColor() == color)
eval += 20;
else
eval -= 20;
}
else if(m_Board[i][j].getType() == Type::PAWN)
{
if(m_Board[i][j].getColor() == color)
eval += 5;
else
eval -= 5;
}
}
}
if(isFinished() == 1) // black
{
(color == Color::BLACK) ? eval += 1000 : eval -= 1000;
}
if(isFinished() == 2)
{
(color == Color::WHITE) ? eval += 1000 : eval -= 1000;
}
if(isFinished(Color::WHITE) == 3 || isFinished(Color::BLACK) == 3)
{
eval -= 1000;
}
return eval;
}
C++ minimax function
New contributor
user24995323 is a new contributor to this site. Take care in asking for clarification, commenting, and answering.
Check out our Code of Conduct.