如何有效地计算顶部排列

时间:2014-02-19 05:06:29

标签: c++ algorithm sorting

我有一个2D字母数组,每个都有一个分数。例如:

J-95 O-90 H-92 N-99
I-91 0-89 L-55
1-80
T-55

从上面的数组中,我想快速获得前20个左右排列(按分数)的列表。在上面的示例中,列表将是:

JOHN
IOHN
J0HN
I0HN
... etc

我目前正在使用递归函数执行此操作 - 但它比我想要的慢。有没有什么好方法可以快速获得前N名单?我的代码是C ++(如果有很好的库建议)。

由于

编辑:

我使用Sneftel和Ethan的答案组合解决了这个问题。我使用修剪函数根据权重减少可能的字符,然后根据权重计算排列。

3 个答案:

答案 0 :(得分:2)

首先,您需要对候选人进行排序。它需要O(nlgn)时间。

N-99 J-95 H-92 I-91 O-90 0-89 1-80 L-55 T-55

其次,根据您需要的最佳分数,您可以选择前n个字符来进行排列。

(n)*(n-1)*(n-2)*(n-3) / (1 * 2 * 3 * 4) >= m. 

n是您选择的候选人数量。 m是您需要的最佳分数。例如,如果您需要20个最佳分数,则只能设置7个字符。可能你面临的问题是你对所有候选人进行排列,而对于一些非常低的候选人来说这是一种浪费。


第三步是获取所需的所有排列,然后对其进行排序和打印。

答案 1 :(得分:2)

这个问题实际上是NP完全的;它是“多选背包问题”(MCKP)的一种形式。

一个可能适合你的简单方法是从每个槽中的前1个字母生成组合,然后是每个槽中的前2个字母,然后是前3个等,并连续两次迭代停止产生相同的前20个分数。这不能保证比强力搜索更有效,但它实现起来很简单,并且适用于“一般”情况。

答案 2 :(得分:0)

有关perm代码的示例,rosetta代码在许多语言this is in c++中都有一些很好的例子。一旦你的排列代码工作,你可以返回biggestcore函数,也可以使用地图将单词映射到分数。

    char** permutations(char *word, int len){
        ... //the perm code
    }
    //returns array of cstrings permutations

    char** returnBiggestScore(char **permutations, int len){
        ...// your score logic goes here
    }
    //would return the top five say, 

在您的主程序中,您可以执行以下操作:

returnBiggestScores(permutations("hello"));

你如何编写你的回报最高分由你决定,但我建议使用一个地图对象, 这样你可以像往常一样检查任意字母的得分:

score['B']; //fast and convinient returns score value for key 'B'