C 如何在回溯中找到所有可能的解决方案

C 如何在回溯中找到所有可能的解决方案,c,backtracking,C,Backtracking,我正在尝试实现一个回溯算法(它应该在给定数量的人中运行,并检查所有可能的对,每对都有一定的分数,目标是找到“最大”分数出现的次数;因此我需要检查所有可能的解决方案) 问题是我不明白如何让我的函数真正“回溯”。。。当它找到一个解决方案时,它会一直回到根目录。我如何回到一个点,我可以尝试一个不同的路径,并使它走那条路径,而不是做同样的一次 这是我的代码,虽然我知道我的想法可能是错误的。。。只是我试着从很多方面来思考,我在这里完全迷失了方向。 谢谢你的帮助 void allPairs (int x,

我正在尝试实现一个回溯算法(它应该在给定数量的人中运行,并检查所有可能的对,每对都有一定的分数,目标是找到“最大”分数出现的次数;因此我需要检查所有可能的解决方案)

问题是我不明白如何让我的函数真正“回溯”。。。当它找到一个解决方案时,它会一直回到根目录。我如何回到一个点,我可以尝试一个不同的路径,并使它走那条路径,而不是做同样的一次

这是我的代码,虽然我知道我的想法可能是错误的。。。只是我试着从很多方面来思考,我在这里完全迷失了方向。 谢谢你的帮助

void allPairs (int x, int pref[], bool teamed[], int* max, int score, int numWorkers) {
    for (int i=1; i < numWorkers; i++) {
        int count = 0;
        pairTwo(x, i, pref, teamed, max, score, numWorkers, &count);
    }
}

int pairTwo (int x, int y, int pref[], bool teamed[], int* max, int score, int numWorkers, int* howMany) {
        if (x >= numWorkers) {
            arrToZero(teamed, numWorkers);
            return score;
        }
        else if (x==y) {
            if(y < numWorkers-1) {
                y = findUnteamed(teamed, y+1, numWorkers);
            }
            else {
                arrToZero(teamed, numWorkers);
                return score;
            }
        }

        int pairScore = sumPair(pref, x, y, teamed, numWorkers);
        x = findUnteamed(teamed, x, numWorkers);
        y = findUnteamed(teamed, 0, numWorkers);
        int temp = pairTwo(x, y, pref, teamed, max, score + pairScore, numWorkers, howMany);
        teamed[x] = 0; // here I tried to "erase" the last move but it's useless
        teamed[y] = 0;
        if (temp >= *max) {
            max = &temp;
            *howMany++;
            printf("There are %d optimal pairings:, with a total score of: %d\n", *howMany, *max);
            return *max;
        }
        else {
        return -1;
        }
}
void allPairs(int x,int pref[],bool teamed[],int*max,int score,int numWorkers){
对于(int i=1;i=numWorkers){
arrToZero(团队、numWorkers);
返回分数;
}
else如果(x==y){
如果(y=*最大值){
最大值=&temp;
*有多少个++;
printf(“有%d个最佳配对:,总分为:%d\n”,*有多少个,*最大值);
返回*最大值;
}
否则{
返回-1;
}
}

如果您不遵循回溯所遵循的精确算法,则回溯会令人困惑。回溯算法中方法的非官方名称被广泛接受,这有助于更轻松地调试代码

标准的递归回溯算法由solve()、get继任者()、isGoal()和isValid()组成。使用一个要计算的整数数组示例,solve()函数如下所示:

int[] solve(int[] list) {
    if ( isGoal( list ) ) {
        return list;
    }
    int[][] successors = getSuccessors( list )
    for (int[] successor : successors) {
        if ( isValid( successor ) ) {
            if ( sizeof( solve( successor ) ) != 0 ) {
                return successor;
            }
        }
    }
    return [];
}
其中,
get继任者()
返回当前数组的深度副本列表,这些副本已被修改以探索新的解决方案,
isGoal()
检查是否已找到解决方案,
isValid()
检查是否有可能找到继续沿着当前路径的目标。这三个函数针对您试图解决的问题


或者,存在一个迭代版本的solve(),初始状态放在一个空堆栈中,尽管您首先需要构造一个堆栈。查看Wikipedia页面上的迭代回溯,了解解决方法是如何工作的。

如果您不遵循它所遵循的精确算法,回溯会令人困惑。回溯算法中方法的非官方名称被广泛接受,这有助于更轻松地调试代码

标准的递归回溯算法由solve()、get继任者()、isGoal()和isValid()组成。使用一个要计算的整数数组示例,solve()函数如下所示:

int[] solve(int[] list) {
    if ( isGoal( list ) ) {
        return list;
    }
    int[][] successors = getSuccessors( list )
    for (int[] successor : successors) {
        if ( isValid( successor ) ) {
            if ( sizeof( solve( successor ) ) != 0 ) {
                return successor;
            }
        }
    }
    return [];
}
其中,
get继任者()
返回当前数组的深度副本列表,这些副本已被修改以探索新的解决方案,
isGoal()
检查是否已找到解决方案,
isValid()
检查是否有可能找到继续沿着当前路径的目标。这三个函数针对您试图解决的问题


或者,存在一个迭代版本的solve(),初始状态放在一个空堆栈中,尽管您首先需要构造一个堆栈。查看Wikipedia页面上的迭代回溯,了解该求解方法的工作原理。

您对
pairTwo
的递归调用必须处于循环中,以检查所有可能性,
x
y
必须在所有未命名的,不仅仅是第一个找到的。对
pairTwo
的递归调用必须处于循环中,以检查所有可能性,
x
y
必须迭代所有未命名的对象,而不仅仅是第一个找到的对象。