非递归最有效的Big-O排列Alghoritm Python3(非内置)

时间:2019-04-06 18:40:45

标签: python-3.x big-o permutation memory-efficient

嗨,伙计们,对于我的数据结构分配,我必须找到最有效的方法(从大到大)来计算对象列表的排列。

我在网络上找到了递归示例,但这似乎并不是最有效的方法。我尝试了自己的代码,但后来我意识到,当我计算可能的排列数时,实际上是在将算法设为O(!n)。有什么建议么? .-。

from random import sample
import time
start = time.time()

testList = list(x for x in range(7))
print('list lenght: %i objects' % len(testList))

nOfPerms = 1
for i in range(1,len(testList)+1):
    nOfPerms *= i
print('number of permutations:', nOfPerms)

listOfPerms = []
n = 1
while n <= nOfPerms:
    perm = tuple(sample(testList, len(testList)))

    listOfPerms.append(perm)
    permutations = set(listOfPerms)

    if len(permutations) == len(listOfPerms):
        n += 1
    else:
        del(listOfPerms[-1])

end = time.time() - start
print('time elapsed:', end)

输出:

list lenght: 7 objects
number of permutations: 5040
time elapsed: 13.142292976379395

如果我将8或9或10代替7,则是排列的数量(由于时间太长,我不会显示时间):

list lenght: 8 objects
number of permutations: 40320

list lenght: 9 objects
number of permutations: 362880

list lenght: 10 objects
number of permutations: 3628800

1 个答案:

答案 0 :(得分:1)

我相信这将是您可以做的最好的事情。生成列表的排列数将生成n!排列。当您需要生成它们时,这还需要花费多少时间(O(n!))。您可以尝试做的是使其成为python生成器函数,以便始终只生成所需数量的函数,而不是预先计算所有函数并将其存储在内存中。如果您想要一个例子,我可以给您一个。

很抱歉,这可能是一个否定的答案。这是一个很好的问题,但我很确定这是渐近地关于您能做的最好的事情。您可以对代码本身进行一些优化,以使用更少的指令,但最终并不会带来太多帮助。

编辑:

这是我承诺的Heap算法的python实现 (https://en.wikipedia.org/wiki/Heap%27s_algorithm)产生N!排列,其中每个排列的生成都需要摊销O(1)时间,并且使用O(n)空间复杂度(通过alteri


def permute(lst, k=None):
    if k == None:

        k = len(lst)

    if k == 1:
        yield lst
    else:
        yield from permute(lst, k-1)

        for i in range(k-1):

            if i % 2 == 0:
                #even
                lst[i], lst[k-1] = lst[k-1], lst[i]
            else:
                #odd
                lst[0], lst[k-1] = lst[k-1], lst[0]
            yield from permute(lst, k-1)


for i in permute([1, 2, 3, 4]):
    print(i)