C匹配算法(使用递归+置换)

时间:2013-01-31 11:11:49

标签: c algorithm recursion matching

我已经找到了很多关于这个主题的研究,这个研究与我想要的很接近,但并不完全正确。似乎许多作业被迫找到字符串的排列,这有类似的方法。我是递归的新手,因此很难跟踪代码。我在另一篇文章中找到了这个片段:

void swap(char* str, int i, int j)
{
    char temp = str[i];
    str[i] = str[j];
    str[j] = temp;
}

void permute(char *string, int start, int end)
{
    if(start == end)
   {
        printf("%s\n", string);
        return;
    }

    permute(string, start + 1, end);
    int i;
    for(i = start + 1; i < end; i++)
    {
        if(string[start] == string[i])
            continue;
        swap(string, start, i);
        permute(string, start + 1, end);
        swap(string, start, i);
    }
}

从那里我可以看到基本情况是字符串的长度与i的索引相同。但是,对于我的任务,我们要做一些稍微不同的事情。我们被要求在可能的夫妻之间扮演“匹配者”。给予我们相同数量的男性和女性,每个人都有“可匹配性”的衡量标准。我们的目标是最大化这个匹配数。因此,如果是3名男性* 3名女性(总是会成为完美的夫妻人数),我会:

 {[M1, W1], {[M1, W1], {[M1, W2],
  [M2, W2],  [M2, W3],  [M2, W1],
  [M3, W3]}  [M3, W2]}  [M3, W3]}
  ....
  // Match #(n)! or in this case 6 (3*2*1)

;

等等。我知道结果的排列数将是(n)!其中n是夫妻的数量。因此,10名男性和10名女性将是(10)!解决方案。考虑到这一点,我发现这个代码与我应该寻找的类似,还是需要修改?我相信必须进行修改,因为这是在线性阵列,我的情况可以是置换两个独立的阵列。

你们有什么想法?

1 个答案:

答案 0 :(得分:1)

您不需要置换2个单独的阵列 - 您只需要置换其中一个阵列,并在匹配时保持另一个不变。这足以保证您检查所有可能的解决方案,以匹配男性和女性。证明很简单,Men只是女性的指数,女性阵列的所有排列只是找到了所有方式来命令它们 - 即为女性指定所有可能性。

让我们来看一个3男3女的简单例子:

data = [M1,M2,M3] [W1,W2,W3]
opt1: M1+W1, M2+W2, M3+W3
opt2: M1+W1, M2+W3, M3+W2
opt3: M1+W2, M2+W1, M3+W3
opt4: M1+W2, M2+W3, M3+W1
opt5: M1+W3, M2+W1, M3+W2
opt6: M1+W3, M2+W2, M3+W1

很容易看到这些是所有的可能性而且我们只更换了女性数组([W1,W2,W3])而男性数组保持不变。


修改
根据您已有的代码,可以这样做:

int permute(int men[], int women[], int start, int end)
{
    if(start == end)
   {
        int i =0, sum = 0;
        for (i = 0; i < end; i++) sum += score(men[i],women[i]);
        return sum;
    }
    best = -INFINITY;
    best = max(permute(men, women, start + 1, end), best);
    int i;
    for(i = start + 1; i < end; i++)
    {
        if(women[start] == women[i])
            continue;
        swap(string, start, i);
        best = max(permute(men, women, start + 1, end), best);
        swap(women, start, i);
    }
    return best;
}

以上只会置换women,并且在stop子句中检查得分(假设为int)并返回迭代中找到的“最佳”得分(假设这里的最高得分最高)。 我还假设你有一些函数int score(int,int)可以找到每场比赛的分数

注意:这是一个c风格的伪代码,它未经过测试,可能存在一些语法问题。