字符串Python上的count操作的计算成本是多少?

时间:2016-03-07 22:51:42

标签: python python-2.7 big-o

例如:

'hello'.count('e')

这是O(n)吗?我猜它的工作方式是它扫描'hello'并在每次看到字母'e'时递增计数器。我如何在不猜测的情况下知道这一点?我尝试阅读源代码here,但却发现了这个问题:

def count(s, *args):
    """count(s, sub[, start[,end]]) -> int

    Return the number of occurrences of substring sub in string
    s[start:end].  Optional arguments start and end are
    interpreted as in slice notation.

    """
    return s.count(*args)

我在哪里可以阅读s.count(*args)中执行的内容?

编辑:我理解*args在Python函数的上下文中的作用。

3 个答案:

答案 0 :(得分:7)

str.countstringobject.c文件的本机代码中实现,该文件委托给stringlib_countPyUnicode_Count,后者本身再次委托给stringlib_countstringlib_count最终使用fastsearch来搜索字符串中子字符串的出现次数并对其进行计数。

对于单字符字符串(例如您的'e'),它会与以下代码路径短路:

for (i = 0; i < n; i++)
    if (s[i] == p[0]) {
        count++;
        if (count == maxcount)
            return maxcount;
    }
return count;

所以是的,这就像你假设对字符串序列的简单迭代并计算子字符串的出现一样。

对于长于单个字符的搜索字符串,由于处理重叠等原因,它会变得有点复杂,并且逻辑被深埋在fastsearch实现中。但它基本上是相同的:通过字符串进行线性搜索。

所以是的,str.count处于线性时间,O(n)。如果你考虑一下,它就会很有意义:为了知道子串出现在字符串中的频率,你需要查看相同长度的每个可能的子串。因此,对于子字符串长度为1,您必须查看字符串中的每个字符,从而为您提供线性复杂性。

顺便说一下。有关基础快速搜索算法的更多信息,请参阅this article on effbot.org

对于只有一个Unicode字符串类型的Python 3,实现的链接是:unicode_count使用stringlib_count使用fastsearch

答案 1 :(得分:1)

很多python的库代码都是用C语言编写的。您正在寻找的代码在这里:

http://svn.python.org/view/python/trunk/Objects/stringobject.c?view=markup

 map( { (.name): del(.name) } ) | add

答案 2 :(得分:1)

如果你追求@ AJNeufeld的回答,你最终会遇到这个链接,它解释了(然后)新的查找逻辑是如何工作的。它是多种字符串搜索方法的组合,旨在从一些逻辑中受益,但避免了搜索的前期表设置成本:http://effbot.org/zone/stringlib.htm

Boyer-Moore是一种着名的字符串搜索算法。 BM-Horspool和BM-Sunday是以某种方式改进原版的变种。谷歌会发现你比你想知道的更多。