我有一个包含200,000个单词和一组字母的字典。我需要一个算法来检查一个单词的所有字母是否都在那组字母中。一个接一个地检查单词很慢。因为需要处理大量的单词,所以我需要一个数据结构来完成这项工作。有任何想法吗?谢谢!
例如:我有一组字母{b,g,e,f,t,u,i,t,g,n,c,m,m,w,c,s},我想检查一下单词“big”和“buff”。所有“大”的字母都是原始集的子集,然后“大”是我想要的,而“buff”不是我想要的,因为原始集合中只有一个“f”。 这就是我想做的事。
答案 0 :(得分:7)
这适用于Scrabble或Boggle,对吧?那么,你要做的是通过排序每个单词中的字母来预生成你的字典。因此,word
变为dorw
。然后将所有这些推入Trie数据结构中。因此,在您的Trie中,序列dorw
将指向值word
。
[请注意,因为我们对单词进行了排序,所以它们会失去唯一性,因此一个排序单词可以指向多个不同的单词。 即您的Trie需要在其数据节点上存储列表或数组]
如果您需要在以后快速加载它而不进行所有排序步骤,则可以保存此结构。
您接下来要做的就是输入输入字母,然后对它们进行排序。然后你开始递归地走过你的Trie。如果当前字母与Trie中的现有路径匹配,则按照它进行操作。因为你可以使用未使用的字母,所以你也可以删除当前的字母。
就这么简单。每当你在Trie中遇到一个有一个值的节点时,你就可以用你用来到那里的字母来表达。您只需在找到它们时将这些单词添加到列表中,并且在递归完成后,您已找到所有可能的单词。
如果输入中有重复的字母,则可能需要额外的逻辑来防止给出同一个单词的多个实例(除非你想要这样)。这个逻辑可以在“遗漏”一个字母(你只是跳过所有重复的字母)到下一个字母的步骤中调用。
[编辑]你似乎想做相反的事情。我上面的解决方案找到了所有可能由一组字母组成的单词。但是你想测试一个特定的单词,看看它是否允许,给定你的字母组。
这很简单。
将可用字母存储为直方图。也就是说,对于每个字母,您存储您拥有的数字。然后,您可以浏览测试单词中的每个字母,随时构建新的直方图。只要您的一个直方图存储桶超过可用字母中的值,就无法生成该字。如果你一直到最后,你可以成功地说出这个词。
答案 1 :(得分:0)
您可以使用数组来标记字母集。数组中的每个元素代表一个字母。要将字母转换为元素位置,只需要减去“a”或“A”的ASCII码。然后第一个元素代表'a',然后第二个元素代表'b',依此类推。然后第27个是'A'。元素值代表事件的发生。例如,数组{2,0,1,0,...}代表类似{a,c,a}。伪代码可以是:
for each word copy the array to a new one for each letter in the word get the element position of the letter: position = letter - 'a' decrease the element value in the new array by one: new_array[position]-- if the value is negative, return not found: if array[position] < 0 {return not found;}
答案 2 :(得分:0)
对集合进行排序,然后对每个单词进行排序并执行“合并”类操作