简体   繁体   English

Python Function 涉及列表操作的时间复杂度

[英]Time complexity of Python Function Involving List Operations

When I plot the time taken for the following algorithm for different size input, the time complexity appears to be polynomial.当我在 plot 为不同大小输入的以下算法所花费的时间时,时间复杂度似乎是多项式的。 I'm not sure which operations account for this.我不确定是哪些操作导致了这一点。

I'm assuming it's to do with list(s) , del l[i] and l[::-1] , but I'm not clear what the complexity of these is individually.我假设它与list(s)del l[i]l[::-1] ,但我不清楚这些单独的复杂性是什么。 Can anyone please explain?谁能解释一下?

Also, is there a way to optimize the algorithm without completely changing the approach?另外,有没有办法在不完全改变方法的情况下优化算法? (I know there is a way to bring it down to linear time complexity by using "double-ended pincer-movement".) (我知道有一种方法可以通过使用“双端钳形运动”将其降低到线性时间复杂度。)

def palindrome_index(s):
    for i, c in enumerate(s):
        l = list(s)
        del l[i]
        if l[::-1] == l:
            return i
    return -1

Your algorithm indeed is quadratic in len(s) :您的算法在len(s)中确实是二次的:

In iteration i , you perform linear time operations in the length: creating the list, reversing it, and (on linear on average) erasing element i .在迭代i中,您在长度上执行线性时间操作:创建列表、反转它,以及(平均线性地)擦除元素i Since you perform this len(s) times, it is quadratic in len(s) .由于您执行此len(s)次,因此它在len(s)中是二次的。

I'm assuming it's to do with list(s), del l[i] and l[::-1], but I'm not clear what the complexity of these is individually.我假设它与列表、del l[i] 和 l[::-1] 有关,但我不清楚这些单独的复杂性是什么。 Can anyone please explain?谁能解释一下?

Each of these operations is linear time (at least on average, which is enough to analyze your algorithm).这些操作中的每一个都是线性时间(至少平均而言,这足以分析您的算法)。 Constructing a list, either from an iterable, or by reversing an existing list, is linear in the length of the list.从可迭代的或通过反转现有列表来构造列表,在列表的长度上是线性的。 Deleting element i , at the very least, requires about n - i + 1 shifts of the elements, as each one is moved back once.删除元素i至少需要大约n - i + 1次移动元素,因为每个元素都向后移动一次。

All of these are linear "O(n)":所有这些都是线性的“O(n)”:

list(s)

list(s) creates a new list from s . list(s)s创建一个新列表。 To do that, it has to go through all elements in s , so its time is proportional to the length of s .为此,它必须通过s中的所有元素 go ,因此其时间与s的长度成正比。

l[::-1]

Just like list(s) , l[::-1] creates a new list with the same elements as l , but in different order.就像list(s)一样, l[::-1]创建一个新列表,其元素与l相同,但顺序不同。 It has to touch each element once, so its time is proportional to the length of l .它必须接触每个元素一次,因此它的时间与l的长度成正比。

del l[i]

In order to delete an element at position i , the element which was at position i+1 has to be moved to position i , then element which was at i+2 has to be moved to position i+1 etc. So, if you are deleting the first element ( del l[0] ), it has to touch move elements of the list and if you are deleting the last ( del l[-1] ), it just has to remove the last. In order to delete an element at position i , the element which was at position i+1 has to be moved to position i , then element which was at i+2 has to be moved to position i+1 etc. So, if you正在删除第一个元素( del l[0] ),它必须触摸移动列表的元素,如果您要删除最后一个元素( del l[-1] ),它只需要删除最后一个。 On average, it will move n/2 elements, so it is also linear.平均而言,它将移动n/2元素,因此它也是线性的。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM