两个列表之间匹配和计数的时间复杂度

时间:2015-03-07 18:57:46

标签: python time-complexity

n_dicwords = [np.sum([c.lower().count(w.decode('utf-8')) for w in dictionary])
                                                for c in documents]

这里我试图确定我的特征工程计算时间:

通过使用这一行代码,该代码遍历每个文档并检查是否以及是否有多少单词也出现在我的字典中,它会生成一个名为 n_dicwords 的功能。对不起,我是复杂性理论的菜鸟,我认为生成这个特征的时间复杂度是O(n * m * w),其中n是文档的数量,m是每个文档中的单词数,w是数字字典中的单词。我对吗?如果有,有什么办法可以改善这个吗?

非常感谢你!非常感谢您的帮助!

2 个答案:

答案 0 :(得分:1)

我有点惊讶地注意到python中的“x in s”构造是O(n),其中n是列表中的项目数。所以,你的估计是正确的。一种更正确的查看方式:由于您所说的文档或工作数根本没有变化,重要的数字是必须检查的单词总数,以及它们所依据的字典长度检查。显然,这根本不会改变计算次数,它只会使我们得到一种可快速识别的O(m * n)形式。

您可以将字典存储在二叉树中,这会将其减少为O(log(n))。

在Google上搜索“二叉树python”,我在那里有一些有趣的东西,就像一个名为“bintrees”的软件包。

然而,Erik Vesteraas指出python'set'数据结构是一个基于散列的集合,在平均情况下复杂度为O(1),O(n)在最坏的情况下非常罕见

请参阅https://docs.python.org/2/library/stdtypes.html#set

答案 1 :(得分:1)

除非你的代码下面的代码有任何巧妙的东西,否则你的复杂性分析应该是正确的。

如果这部分的表现很重要,你应该使用多模式字符串搜索算法,该算法试图解决你正在做的几乎所有问题。

首先看一下最常用的Aho-Corasick并以线性时间运行。谷歌搜索“Aho-Corasick python”出现了几个不同的实现,所以虽然我没有亲自使用它们,但我认为你不必实现算法本身来使用它。

如果你只是需要你的代码运行得更快,并且不需要获得最佳性能,你可能只需要使用字典集。在python中,普通集是一个哈希集,因此它具有恒定的时间查找。然后你可以只为每个单词检查它是否在字典中。