最小阿尔法贝塔的路径

Path of minimaxalpha beta

本文关键字:路径 贝塔 阿尔法      更新时间:2023-10-16

好吧,我有一个吃豆人游戏,带有全局向量字符位置,每个字符的行,列...( 例如:字符 [0] 是重影 1 的行,字符 [1] 是重影 1 的列,字符 [2] 是重影 2 的行...字符[8]和字符[9]是吃豆人行和列。

我的最小最大字母表实现是:

int minimaxAlphaBeta ( int mazeTemp[][COLUMNS], int alpha, int beta, int score, int direction, int depth, int jugador)
{
    int bestValue, childValue;
    int playerRow=2*jugador;
    int playerColumn=(2*jugador)+1;
    int sr= CharactersLocationsMaze[playerRow];
    int sc= CharactersLocationsMaze[playerColumn];
    bool restore=false;
    if(mazeTemp[sr][sc] == WALL) //You cannot visit it, or is wall or is @ visited
            return 0;
    if( depth > 0)
    {
        //El fantasma gana ya que esta en la misma posicion que el pacman
        if (sr == CharactersLocationsMaze.at(8)  &&  sc == CharactersLocationsMaze.at(9) )
            {
            bestValue=10000;
            return bestValue;
            }
        else if ( PacmanWin(mazeTemp))
                {
                 bestValue=-10000;
                 return bestValue;
                }
    }
    else if (depth==0)
            {
            bestValue= abs( CharactersLocationsMaze.at(0)- CharactersLocationsMaze.at(8) ) +
                       abs( CharactersLocationsMaze.at(2)- CharactersLocationsMaze.at(8) ) +
                       abs( CharactersLocationsMaze.at(4)- CharactersLocationsMaze.at(8) ) +
                       abs( CharactersLocationsMaze.at(6)- CharactersLocationsMaze.at(8) ) +
                       abs( CharactersLocationsMaze.at(1)- CharactersLocationsMaze.at(9) ) +
                       abs( CharactersLocationsMaze.at(3)- CharactersLocationsMaze.at(9) ) +
                       abs( CharactersLocationsMaze.at(5)- CharactersLocationsMaze.at(9) ) +
                       abs( CharactersLocationsMaze.at(7)- CharactersLocationsMaze.at(9));
            // score se podria modificar ( penalizas mas perder puntos o alejarte del pacman
            bestValue=((1/bestValue)*Number_MAX_VALUE)-(score*10);
            return bestValue;
            }
    //puntuacion pacman si consigue puntos
    else  if (jugador < 4)
            { // Jugadores 0,1,2,3 son fantasmas maximizan valor
            bestValue = alpha;  //bestvalue es lmax y childValue l
            bestMovementPath.push_back(direction);
            //Row --  Norte: jugador Actualizo el valor de lmin porque l es menor que lmin
            CharactersLocationsMaze[playerRow]=sr-1;
            CharactersLocationsMaze[playerColumn]=sc;
            childValue = minimaxAlphaBeta( mazeTemp, bestValue, beta, score, 1, depth-1, jugador+1);
            if(childValue > bestValue) bestValue = childValue;
            //Row ++  Sur
            CharactersLocationsMaze[playerRow]=sr+1;
            CharactersLocationsMaze[playerColumn]=sc;
            childValue = minimaxAlphaBeta( mazeTemp, bestValue, beta, score, 2, depth-1, jugador+1);
            if(childValue > bestValue) bestValue = childValue;
            //Column --  Oeste West
            CharactersLocationsMaze[playerRow]=sr;
            CharactersLocationsMaze[playerColumn]=sc-1;
            childValue = minimaxAlphaBeta( mazeTemp, bestValue, beta, score, 3, depth-1, jugador+1);
            if(childValue > bestValue) bestValue = childValue;
            //Column ++  Este
            CharactersLocationsMaze[playerRow]=sr;
            CharactersLocationsMaze[playerColumn]=sc+1;
            childValue = minimaxAlphaBeta( mazeTemp, bestValue, score, 4, beta, depth-1, jugador+1);
            if(childValue > bestValue)
               {
                bestValue = childValue;
                if (beta <= bestValue) {
                          return bestValue; //00
                }//Path.append("E");
               }
            //Restore
            CharactersLocationsMaze[playerRow]=sr;
            CharactersLocationsMaze[playerColumn]=sc;
            bestMovementPath.pop_back();
            return bestValue;
            }

    else if ( jugador == 4)
            { // jUGADOR MIN
            bestValue = beta;  //bestvalue es lmax y childValue l
            bestMovementPath.push_back(direction);
            if(mazeTemp[sr][sc] == FOOD)
                               {
                                score=score+1;
                                mazeTemp[sr][sc] == PASSAGE;
                                restore=true;
                                }

            //Row --  Norte: jugador Actualizo el valor de lmin porque l es menor que lmin
            CharactersLocationsMaze[playerRow]=sr-1;
            CharactersLocationsMaze[playerColumn]=sc;
            childValue = minimaxAlphaBeta( mazeTemp, alpha, bestValue, score, 1, depth-1, 0);
            if(childValue < bestValue) bestValue = childValue;
            //Row ++  Sur
            CharactersLocationsMaze[playerRow]=sr+1;
            CharactersLocationsMaze[playerColumn]=sc;
            childValue = minimaxAlphaBeta( mazeTemp, alpha, bestValue, score, 2, depth-1,0);
            if(childValue < bestValue) bestValue = childValue;
            //Column --  Oeste
            CharactersLocationsMaze[playerRow]=sr;
            CharactersLocationsMaze[playerColumn]=sc-1;
            childValue = minimaxAlphaBeta( mazeTemp, alpha, bestValue, score, 3, depth-1, 0);
            if(childValue < bestValue)  bestValue = childValue;
            //Column ++  Este
            CharactersLocationsMaze[playerRow]=sr;
            CharactersLocationsMaze[playerColumn]=sc+1;
            childValue = minimaxAlphaBeta( mazeTemp, alpha, bestValue, score, 4, depth-1,0);
            if(childValue < bestValue)
               {
                bestValue = childValue;
                if ( bestValue <= alpha) {
                               return bestValue;
                             }
               }
            //RESTORE MAZE !!!! restore score ???
            CharactersLocationsMaze[playerRow]=sr;
            CharactersLocationsMaze[playerColumn]=sc;
            if ( restore) mazeTemp[sr][sc] == FOOD;
            bestMovementPath.pop_back();
            return bestValue; //if ( Path.size() > 2) Path.erase(Path.size() - 1);
            }
}

此外,如果jugador(玩家= 4(,是吃豆人,如果它在迷宫中有食物,它会得分。

有三个疑问:如何获得第一个移动(我考虑使用全局变量 bestMovementpath 并将每次迭代推向方向,并在恢复后(。我不知道它是否正确,或者是否有另一种更好、更干净的解决方案。每次调用函数时,我都会清除最佳值运动向量。

另一个是如何在吃豆人玩家(jugador=4(位于食物迷宫中的情况下恢复食物。然后我必须在其他递归中再次恢复到 Food。

最后一个问题是关于测试版,阿尔法...我认为我只根据最佳值削减一次,或者如果我必须在每次比较后削减......

任何帮助将不胜感激...此外,我还定义了一个启发式方法,如果有人可以以一种简单的方式改进它......

提前致谢

为了从递归中获得第一步,您可以尝试将其与 bestValue 一起保存。当您选择了最佳移动并且即将从递归返回时,您可以同时返回 bestValue 和第一个移动,例如使用 std::p air,以便您的方法签名

std::pair<int, int> minimaxAlphaBeta(...);

要恢复食物,请将单元格内容保存在字符变量 prevValue 中,覆盖单元格内容,调用递归,从 prevValue 恢复原始单元格值。架构为

char prevValue = mazeTemp[sr][sc];
mazeTemp[sr][sc] = ' ';
minimaxAlphaBeta(...);
minimaxAlphaBeta = prevValue;

我不确定 alpha-beta 修剪在这里是否合适。它适用于两个玩家"做同样的事情"的 2 人游戏。在这个游戏中,情况并非如此。