为什么递归函数在峰值后向下计数?

时间:2011-11-04 12:55:07

标签: c recursion

担心我可能会超越我的另一个问题(尽管这完全是一个新问题)我仍然会问这个问题。

我有这段代码:

int blob_count(int y, int x, int gridCopy[][5], int sum){

    //Local vars
    int posX, posY;

    //Find the position 1 behind and 1 above the starting point, and start the loop there
    for(posX = -1;posX <=1; posX++){
        for(posY = -1; posY <= 1; posY++){
            if((y + posY) >= 0 && (x + posX) >= 0){
                if((y + posY) <= 5 && (x + posX) <= 5){
                    if(gridCopy[posY+y][posX+x] == 1){
                        //Set the starting point to 0 (so it wont get calculated again)
                        gridCopy[posY+y][posX+x] = 0;



                        y = posY+y;
                        x = posX+x;

                        sum++;
                        blob_count(y, x, gridCopy, sum);
                    }
                }
            }
        }
    }

    return sum;
}

问题是,对于每次递归运行,sum计数为1,返回错误的值。通过为每个递归运行执行打印,它会得到结果:

sum = 1  
sum = 2  
sum = ...  
sum = n  

然而,通过设置打印出for循环之外的总和(在返回总和之前),这是很好的,当它达到峰值时会发生相反的情况,所以它会这样做:

sum = n  
sum = ...  
sum = 2  
sum = 1  

return sum; // = 1

这显然是错误的,因为我想要总数,而不是最低数。我的返回值是否错误?我已经尝试在递归调用之后(在循环内)将其放入,但无济于事。

2 个答案:

答案 0 :(得分:1)

pmg说什么。对于每个递归调用,将复制sum的当前值,并将副本传递给递归调用。如果要修改函数中的对象,则必须将指针传递给这些对象而不是对象本身。

答案 1 :(得分:1)

好吧,让我们摆脱额外的比特,将问题简化为必需品。 你有:

int blob_count(int sum)
{
    sum++;

    if (sum < 10)
        blob_count(sum);

    return sum;
}

如果你在printf("sum==%d\n", sum)之前添加return,那么它将在最里面的递归(其中sum == 10)首先被调用,然后它会return到下一个级别其中sum == 9,打印,返回sum == 8等等。

如果您在递归调用blob_count(sum)之前将其放入,那么您将在递归之前打印这些值,因此它们从sum==0, sum == 1开始,依此类推。


如果你想让sum成为递归所达到的最深层次,那么你可以通过返回值将它传回去:

int blob_count(int sum)
{
    sum++;

    if (sum < 10)
        sum = blob_count(sum);

    return sum;
}

或者您可以通过指针传递它,以便修改原始变量:

void blob_count(int* sum)
{
    *sum++;

    if (*sum < 10)
        blob_count(sum);

    return;
}

第一个可能是您正在寻找的解决方案。