2015-10-26 55 views
1

我有一個列表的列表,我們可以認爲它是3個球的3個球。itertools和從分區集合中選擇

mylist= [ 
      ['HIGH_1', 'MED_1', 'LOW_1'], 
      ['HIGH_2', 'MED_2', 'LOW_2'], 
      ['HIGH_3', 'MED_3', 'LOW_3'] 
     ] 

我只允許從每個甕中選擇一個球。 我想獲得1球,2球和3球的所有組合。在列表中回答。

爲了實現這一點,我在每個

mylist= [ 
      [None, 'HIGH_1', 'MED_1', 'LOW_1'], 
      [None, 'HIGH_2', 'MED_2', 'LOW_2'], 
      [None, 'HIGH_3', 'MED_3', 'LOW_3'] 
      ] 

放置一個假元件(無)現在以下使用itertools的和過濾器獲取我所需的解決方案。

combos = [] 
for l in itertools.product(*mylist): 
    combos.append(filter(lambda a: a is not None, l)) 

combos.remove(()) # remove the empty element 
print [list(elem) for elem in combos] 


[['HIGH_3'], ['MED_3'], ['LOW_3'], ... , ['MED_2', 'HIGH_3'], ['MED_2', 'MED_3'], ['MED_1', 'HIGH_3'], ..., ['LOW_1', 'LOW_2', 'MED_3'], ['LOW_1', 'LOW_2', 'LOW_3']] 

其中產生63個元素。

9(單元素)+ 27(兩個元素)+ 27(三要素)= 63

添加在假和後過濾不覺得自己做到這一點的最好辦法。

有沒有辦法避免這兩個看似多餘的步驟?

+3

那麼你寫了什麼,究竟是什麼問題呢? – jonrsharpe

+0

你有*「更好」*的標準嗎? – jonrsharpe

回答

1

您可以用下面的發電機

def combos(data): 
    for i in xrange(1, len(data) + 1): 
     for item in itertools.combinations(data, i): 
      for j in itertools.product(*item): 
       yield j 

也許最Python的解決方案,我能想到的做到這一點。

0

當您只附加非空項目時,您不需要remove()。您也可以通過在過濾器之後立即將項目轉換爲列表來跳過最後的列表理解。

import itertools 
import pprint 

mylist= [ 
      [None, 'HIGH_1', 'MED_1', 'LOW_1'], 
      [None, 'HIGH_2', 'MED_2', 'LOW_2'], 
      [None, 'HIGH_3', 'MED_3', 'LOW_3'] 
      ] 
combos = [] 
for item in itertools.product(*mylist): 
    combo = list(filter(lambda a: a is not None, item)) 
    if combo: 
     combos.append(combo) 

pprint.pprint(combos) 

UPDATE

手動插入None是不是很好。添加一條線,這是否在列表的理解:

import itertools 
import pprint 

mylist= [ 
      ['HIGH_1', 'MED_1', 'LOW_1'], 
      ['HIGH_2', 'MED_2', 'LOW_2'], 
      ['HIGH_3', 'MED_3', 'LOW_3'] 
      ] 

mylist_with_nones = [[None] + item for item in mylist] 
combos = [] 
for item in itertools.product(*mylist_with_nones): 
    combo = list(filter(lambda a: a is not None, item)) 
    if combo: 
     combos.append(combo) 

pprint.pprint(combos) 
+0

感謝Mike,這有幫助,我希望不必將三個None值添加到我的數組中。看看第一個mylist對象。你可以用這個對象得到想要的結果而不必在每個數組中添加一個None。 – Dickster

+0

您不必手動添加'None'條目。我更新了我的答案,並添加了一條爲您提供幫助的線路。 –