【问题标题】:Fast way to find if list of words contains at least one word that starts with certain letters (not "find ALL words"!)快速查找单词列表是否包含至少一个以某些字母开头的单词(不是“查找所有单词”!)
【发布时间】:2019-12-18 04:35:39
【问题描述】:

我已经设置(不是列表)字符串(单词)。这是一个很大的。 (使用 openCVtesseract 从图像中提取出来,因此没有可靠的方法来预测其内容。)

在使用此列表时,我需要确定它是否包含至少一个以我当前正在处理的部分开头的单词。 所以它就像(不是实际代码):

if exists(word.startswith(word_part) in word_set) then continue else break

关于如何在列表中查找所有以here开头的字符串有一个很好的答案:

result = [s for s in string_list if s.startswith(lookup)]

result = filter(lambda s: s.startswith(lookup), string_list)

但它们返回找到的所有字符串中的listiterator。 我只需要查找集合中是否存在任何这样的字符串,而不是全部获取。 就性能而言,获取列表似乎有点愚蠢,然后获取其 len 并查看它是否大于零,然后删除该列表。

有更好/更快/更清洁的方法吗?

【问题讨论】:

  • 你可以只是re.search("[\b]lookup_term",original_block_of_text)) ...但它仍然是O(N)......你可以制作一组word[:len(lookup_term)]而不是整个单词......但仍然需要O (N) 构建该集合(但随后非常快速查找)...
  • 如果你想短路,为什么不if any(word.startswith(word_part) for word in wordset)
  • 如果你想让这个检查更高效,你应该把你的字符串存储在前缀树中(见这个问题stackoverflow.com/questions/11015320/…或使用真正的库),否则就像其他人一样使用any已经提到了。
  • sort + bisect + startswith
  • Joran Beasely,不,那不行,我需要多次这样做。具有不同的-length 起始字母集。所以建立一个不同的列表来查找性能太重了。克里斯,是的,这正是我所需要的,我刚开始用 python 编码,所以我还不知道“任何”,谢谢! Boris,对于像我这样的前 Web 开发人员来说,这太数据科学了。还不是我的水平,谢谢指点。等我有更多经验时,我会朝这个方向看。

标签: python python-3.x any


【解决方案1】:

您的伪代码非常接近真实代码!

if any(word.startswith(word_part) for word in word_set):
    continue
else:
    break

any 一旦找到一个真正的元素就返回,所以它很高效。

【讨论】:

  • 正是我需要的,谢谢!我刚开始学习 python(大约 10 天前写了我的第一个脚本,它不仅仅是“print('this is a Drill')”-lookalikes),所以有些东西我还没有遇到。
【解决方案2】:

你需要yield:

def find_word(word_set, letter):
    for word in word_set:
        if word.startswith(letter):
            yield word
    yield None
if next(find_word(word_set, letter)): print('word exists')

Yield 懒洋洋地发话。所以如果你调用一次,它只会给出一个单词。

【讨论】:

  • 我认为您不需要强制转换为 iter ...生成器自动成为迭代器 next(find_word(word_set,letter))
  • 这比上面的例子更快/更轻吗?它肯定是更多的代码 :) 但是,绝对方式更易于人类阅读!
  • 计时了,这个比另一个快得多。但现在我不确定为什么。它几乎就像 any 的实现,在另一个答案中使用。 @JoranBeasley 可以详细说明一下吗?
  • 基于 dis.dis 它可能必须构建一个额外的功能......但老实说我有点惊讶它比任何东西都更快......不是被吹走而是惊讶......但是我认为这两种方法非常接近......
  • 在找到this massive difference之前,我也不会被吹走
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2017-10-16
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-07-06
  • 1970-01-01
  • 2013-01-07
相关资源
最近更新 更多