2013-05-09 103 views
1

計算排列數目的最快方法是什麼?我有以下問題:在Python中計算排序

首先我有這:

ncombos = itertools.combinations_with_replacement(['a1', 'a2', 'a3'], years*n) 
('a1', 'a1', 'a1') 
('a1', 'a1', 'a2') 
('a1', 'a1', 'a3') 
('a1', 'a2', 'a2') 
.... etc.....  
('a3', 'a3', 'a3') 

目的是要經過每一個,並計算每一個有排列的數量和構建具有這些值的陣列。我實現這一點使用:

nodes = np.ones(len(leafs)); i=0 #This will store the number of permutations 

for j in ncombos: 
    nodes[i] =len(list(set(itertools.permutations(np.asanyarray(j), n)))) 
    i = i+1 

np.asanyarray(j)的轉換( 'A1', 'A1', 'A1')轉換成正式[ 'A1', 'A1', 'A1'],這是需要排列()來工作。設置擦除相同的排列。列表列出了這個。 len計算我可以用a1,a1,a1進行多少置換。

所以基本上我想要的是統計排列的數量......但是我的代碼非常棒!慢 !謝謝!

+1

你能有所正式定義你的問題?我不明白你想要計算什麼。 – nhahtdh 2013-05-09 02:05:59

回答

8

使用數學。列表的排列數量是列表長度的階乘,除以每個元素的多重性的階乘的乘積(因爲重複元素的集合被置換而沒有效果)。

import operator 
from collections import Counter 
from math import factorial 
def npermutations(l): 
    num = factorial(len(l)) 
    mults = Counter(l).values() 
    den = reduce(operator.mul, (factorial(v) for v in mults), 1) 
    return num/den 

例子:

>>> npermutations([1,1,1]) 
1 
>>> npermutations([1,2,3]) 
6 
>>> npermutations([1,3,1,2,1,3,1,2]) 
420 
+0

我認爲這是相似的,但不同於他想要計算的結果(假設我正確地認爲他想要置換置換,又稱笛卡爾積) – Patashu 2013-05-09 02:11:50

+0

他很清楚地想要置換的數量沒有置換,但他計算對於每個組合都有替換。 (雖然,我有理由相信有一個替代方法來解決他的問題,不會引發組合爆炸......) – nneonneo 2013-05-09 02:13:17

+0

這就是我想要的!它工作完美。雖然我不知道爲什麼,但你的功能比我的方式快得多。任何線索?另外,你會如何讓你的方法更快?有什麼辦法嗎?謝謝! – Oniropolo 2013-05-09 02:20:31

0

如果你想要更換置換,這存在並被稱爲笛卡爾產品。 Itertools具有這樣的功能,product()

>>> for i in itertools.product('ABC', repeat=3): 
...  print i 
... 
('A', 'A', 'A') 
('A', 'A', 'B') 
('A', 'A', 'C') 
('A', 'B', 'A') 
('A', 'B', 'B') 
('A', 'B', 'C') 
('A', 'C', 'A') 
('A', 'C', 'B') 
('A', 'C', 'C') 
('B', 'A', 'A') 
('B', 'A', 'B') 
('B', 'A', 'C') 
('B', 'B', 'A') 
('B', 'B', 'B') 
('B', 'B', 'C') 
('B', 'C', 'A') 
('B', 'C', 'B') 
('B', 'C', 'C') 
('C', 'A', 'A') 
('C', 'A', 'B') 
('C', 'A', 'C') 
('C', 'B', 'A') 
('C', 'B', 'B') 
('C', 'B', 'C') 
('C', 'C', 'A') 
('C', 'C', 'B') 
('C', 'C', 'C')