说我有2套:
Set A: ['hi', 'there', 'hire', 'hih', 'hih543']
Set B: ['hihow', 'himan, 'fsdko45']
现在,这些套装实际上每个都包含近百万个元素。
简而言之,我需要做的是以这种方式过滤集合B
1)对于集合B的每个元素,找到集合A中作为它的前缀的所有元素。
因此,在上面的示例中,当我针对hihow
检查集A时,我得到2个结果:hi
和hih
。
2)说我有max_offset = 3
。对于我在集合A
中得到的每个结果,我应该添加[0,1,2,3]
来设置A元素长度,如果任何结果等于set B元素长度,则返回true。
在这个例子中,我们假设我们从hih
开始,所以我添加了' 1'对它,我添加' 2'对它,我得到一个匹配,hih.size + 2 == hihow.size
。整个操作返回true。
现在,我怎么能以一种我不会等待数小时才完成此操作的方式来做到这一点?我认为我可以使用的一种方法是使1套尝试。假设我们设置B试图允许快速查找。
所以现在,我迭代集合A元素,并检查:集合B的哪些元素是这个元素的前缀?因此对于'hi'
,我得到['hihow', 'himan']
。现在我将[0,1,2,3]
添加到hi.size
,如果结果与数组中任何1个元素的大小相匹配,那么该元素就是匹配。
另一种方法是将集合A设置为尝试,并迭代集合B,在其结尾处删除0-3个字符。所以说我接受hihow
,我产生['hihow', 'hiho', 'hih']
并检查所有三个是否与A集相匹配。是的,那里有匹配,所以这会返回true。
我担心我在这种方法中缺少正确性,所以我在这里发布了它。此外,如果有人有更简单/更好的方法,请告诉我。谢谢!
答案 0 :(得分:1)
使用此gem,找到以前缀开头的单词比查找单词中包含的前缀更容易。
Trie是从B组完成的。对于每个匹配,此代码检查后缀是否最多包含3个字符:
# gem install triez
require 'triez'
prefixes = ['hi', 'there', 'hire', 'hih', 'hih543']
words = ['hihow', 'himan', 'fsdko45']
word_trie = Triez.new
words.each do |word|
word_trie[word] = 1
end
prefixes.each do |prefix|
suffixes = word_trie.search_with_prefix(prefix).select{|suffix, id| suffix.size <=3 }
suffixes.each do |suffix, id|
word = prefix + '|' + suffix
puts word
end
end
# =>
# hi|man
# hi|how
# hih|ow