简体   繁体   English

由于堆栈溢出异常,C#Minimax进程终止

[英]C# Minimax process terminated due to stackoverflowexception

I have been trying to create a tic tac toe game in C# with minimax functionality. 我一直在尝试用C#创建具有最小最大功能的井字游戏。 Unfortunately I'm running into problems with getting the minimax function to correctly work. 不幸的是,我在使minimax函数正常工作方面遇到问题。

    static double MiniMax(char[] gameState, int depth)
    {
        int bestMove = 0;
        double bestScore = -double.PositiveInfinity;
        if (maxDepth > 0)
        {
            for (int i = 0; i < 9; i++)
            {
                if (ValidMove(i, gameState))
                {
                    char[] clone = new char[board.Length];
                    board.CopyTo(clone, 0);
                    clone[i] = 'X';
                    double score = 0;
                    score += MinPlay(clone, maxDepth--);
                    if (score > bestScore)
                    {
                        bestMove = i;
                        bestScore = score;
                    }
                }
            }
        }
        return bestMove;
    }

    static double MinPlay(char[] gameState, int depth)
    {
        if (Win(gameState)) return -1;
        if (Draw(gameState)) return 0;
        double bestScore = double.PositiveInfinity;
        if (maxDepth > 0)
        {
            for (int i = 0; i < 9; i++)
            {
                if (ValidMove(i, gameState))
                {
                    char[] clone = new char[board.Length];
                    board.CopyTo(clone, 0);
                    clone[i] = 'O';
                    double score = 0;
                    score += MaxPlay(clone, maxDepth--);
                    if (score > bestScore)
                    {
                        bestScore = score;
                    }
                }
            }
        }
        return bestScore;
    }

    static double MaxPlay(char[] gameState, int depth)
    {
        if (Win(gameState)) return 1;
        if (Draw(gameState)) return 0;
        double bestScore = -double.PositiveInfinity;
        if (maxDepth > 0)
        {
            for (int i = 0; i < 9; i++)
            {
                if (ValidMove(i, gameState))
                {
                    char[] clone = new char[board.Length];
                    board.CopyTo(clone, 0);
                    clone[i] = 'X';
                    double score = 0;
                    score += MinPlay(clone, maxDepth--);
                    if (score > bestScore)
                    {
                        bestScore = score;
                    }
                }
            }
        }
        return bestScore;
    }

I made these functions by using the guide here: http://giocc.com/concise-implementation-of-minimax-through-higher-order-functions.html 我通过以下指南完成了这些功能: http : //giocc.com/concise-implementation-of-minimax-through-higher-order-functions.html

When running the program everything works fine until the computer has to take its turn. 运行该程序时,一切正常,直到计算机必须轮到它为止。 I get the error "Process is terminated due to StackOverflowException". 我收到错误消息“由于StackOverflowException,进程已终止”。 I think this is caused by infinite recursion but after looking through the program for a while I can't tell what is causing it. 我认为这是由无限递归引起的,但是在浏览该程序一段时间后,我无法确定是什么原因造成的。

I have edited the code so that there is now a depth and the minplay and maxplay loops have a validmove check in them. 我已经编辑了代码,以便现在有了一个深度,并且minplay和maxplay循环在其中进行了有效移动检查。 The the computer now makes a move but for some reason it only ever chooses the first position. 现在,计算机开始移动,但是由于某种原因,它只能选择第一个位置。 If the player chooses the first position as their first move the computer then chooses the position next to it and on the next turn it will over write the player on the first position. 如果玩家选择第一个位置作为他们的第一个举动,那么计算机会选择它旁边的位置,并且在下一回合中它将覆盖玩家在第一个位置上的位置。 Then the computer stops making moves. 然后计算机停止移动。 I have no clue as to why this is happening. 我不知道为什么会这样。

Any help would be much appreciated! 任何帮助将非常感激!

It is being caused because MaxPlay calls the function MinPlay which in turn calls the function MaxPlay again, and you aren't doing anything to change the gamestate after each successive call to cause the recursion to end. 这是因为MaxPlay调用了MinPlay函数,而该函数又又调用了MaxPlay函数,并且您在每次连续调用导致递归结束后都没有做任何更改游戏状态的操作。 You just toggling clone[0] between 'o' and 'x', your functions never complete an iteration of the for loop. 您只是在'o'和'x'之间切换clone [0],您的函数就永远不会完成for循环的迭代。

Change your for loops in MinPlay and MaxPlay to only consider empty squares. 在MinPlay和MaxPlay中将for循环更改为仅考虑空白方块。 It also looks like your not using the gameState that is being passed in. I don't know where board is defined. 看起来您还没有使用传入的gameState。我不知道在哪里定义木板。

for (int i = 0; i < 9; i++)
{ 
    if (ValidMove(i, gameState) {
        char[] clone = new char[gameState.Length];
        gameState.CopyTo(clone, 0);
        clone[i] = 'X';
        double score = MinPlay(clone);
        if (score > bestScore)
        {
            bestScore = score;
        }
    }
}
return bestScore;

EDIT: 编辑:

You changed it to score += which is incorrect. 您将其更改为+ =,这是不正确的。 Also, You have the incorrect score comparison in MinPlay. 此外,您在MinPlay中的分数比较不正确。

    if (score < bestScore)
    {
        bestScore = score;
    }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM