函数不返回负值

时间:2013-12-08 19:13:42

标签: c# function return-value tic-tac-toe alpha-beta-pruning

我正在做一个关于4x4 tic-tac-toe游戏的小项目。我正在使用Alpha Beta Search来寻找下一个最佳动作。在alpha beta搜索中,我使用的是在以下算法的“效用”函数中调用的截止评估函数

Alpha Beta Search

我成功实现了一切,但问题是效用函数没有返回负值,我真的不知道为什么!以下是功能

private static int utility(GameTreeNode gtn, bool isMin = false)
{
    int nodeValue = 0;
    switch (gtn.NodeBoard.getBoardStatus())
    {
        case Status.Success:
            nodeValue = 50;
            if (isMin) nodeValue = -50;    /// here
            break;
        case Status.Incomplete:
            if (isMin)
                nodeValue = gtn.evaluate(State.X);
            else
                nodeValue = gtn.evaluate(State.O);
            break;
    }
    // case Status.Draw:
    return nodeValue;
}
当从MinValue函数

调用它时,

isMin设置为true

isMin是O的移动,AI的移动是X.如果O赢了,该实用程序应该返回-50。 但它只返回0 。我调试了程序,它实际上将-50分配给nodeValue(调试器中的nodeValue更改为-50),但是当我在Min或Max函数中收到时,它为零。

注意:整个项目中使用的所有int都是signed int。如果您认为函数调用者是无符号的

,则不使用unsigned关键字

alpha-beta搜索的完整代码位于:http://pastie.org/8538015

请朋友们,尽快帮助。

1 个答案:

答案 0 :(得分:1)

由于您在方法签名中使用了可选参数,因此我建议您在输入函数时注意实际运行的代码。你说你调试了它并且值被分配了,但我没有足够的上下文来知道它是否只发生在很多情况中的一种情况。无论如何,只要小心那些!

我会像这样重写你的函数:

private static int utility(GameTreeNode gtn, bool isMin)
{
    switch (gtn.NodeBoard.getBoardStatus())
    {
        case Status.Success:
            return isMin 
                ? -50 
                : 50;
        case Status.Incomplete:
            return isMin 
                ? gtn.evaluate(State.X)
                : gtn.evaluate(State.O);
        default:
            throw new NotImplementedException("The status is not implemented.");
    }
}

我用这种方法看到了一些改进:

  • 您不需要存储值并在最后返回它。在您的情况下,当您获取Status.Success路径时,您总是将50存储到nodeValue中,然后有时为其分配-50。除非你坚持一个函数回归,否则我认为这种方法更清晰。可能只是我的意见。
  • switch语句中有一个默认值,以便在状态未实现的情况下显式抛出异常。
  • 您的功能有可选参数。我没有看到使这个参数可选的好处。在我看来,它似乎只是增加了调整内容的空间。

修改

基于以下代码:http://pastie.org/8538015#33,43

if (gtn.Nodes.Count == 0) return utility(gtn, true);函数中点击private static int MinValue(GameTreeNode gtn, int alpha, int beta)时,看起来只有 时间才能获得返回负值的实用程序。否则,除非您没有发布更多代码,否则对实用程序功能的其他调用都不会达到您想要的逻辑路径。你提到当你进入那里时,你可以看到nodeValue的值被正确分配。

我建议你改变:

// if Terminal-test(state) then return utitly(state)
if (gtn.Nodes.Count == 0) return utility(gtn, true);
gtn.Value = Globals.MAXINT;

// if Terminal-test(state) then return utitly(state)
if (gtn.Nodes.Count == 0)
{
    int retVal = utility(gtn, true);
    return retVal;
}

gtn.Value = Globals.MAXINT;

至少暂时,然后在return retVal上设置一个断点。如果您的效用函数 实际设置了您所期望的值,那么当它返回MinValue函数时,它无法神奇地消失。我有一种感觉可疑的事情并且代码实际上没有执行你期望的路径。