我有一个有趣的问题。我有一个包含分层数据的列表。
relation = [('grandfather'), ('father'), ('son')]
从某种意义上说,如果没有son
就不能有grandfather
,但father
可能没有son
。
每个条目都可以有一个状态。
status = [('tall'), ('short')]
我试图找到所有可能的组合,这是有道理的。这就是组合
combination_sense = [('grandfather', 'tall'), ('father', 'short'), ('son', 'short')]
可能存在,但组合
combination_no_sense = [('grandfather', 'tall'), ('son', 'short')]
可能不存在,因为son
没有father
。
同样,组合
combination_sense = [('grandfather', 'tall'), ('father', 'short')]
确实可能存在。
我用itertools
尝试了自己。我尝试了list(itertools.product())
和itertools.permutations()
,但我无法使其正常工作。
如何处理层次关系?帮助非常有用!
答案 0 :(得分:2)
如果我理解正确,您希望从两个列表中生成所有值的组合,但您对列表的处理方式与对方不同。
对于第一个分层列表,您必须始终使用第一个值,并且只要您不跳过任何值,就可以将值序列扩展任何数量。因此,对于您的示例列表,您将生成['grandfather'], ['grandfather', 'father'], ['grandfather', 'father', 'son']
。
对于第二个列表,您希望所有组合(替换)与您要与之配对的层级值的长度相同。
这不应该与自定义生成器功能有关:
import itertools as it
def combine(relations, statuses):
for i in range(len(relations)):
relation = relations[:i+1]
for status_combination in it.product(statuses, repeat=i+1):
yield list(zip(relation, status_combination))
首先从较小的结果开始(例如仅包含'grandfather'
的结果)。如果您想从最长的(包含'son'
的那些)开始,您可以将上面代码中的i+1
的两个实例替换为len(relations)-i
。
如果您想要relations
的所有连续子序列(因此['father', 'son']
将被允许,['father']
和['son']
本身也是如此),您可以只做一些更改以获得该结果:
import itertools as it
def combine(relations, statuses):
for start, stop in it.combinations(range(len(relations) + 1), 2): # get two indexes
relation = relations[start:stop] # slice using both
for status_combination in it.product(statuses, repeat=stop-start): # use difference
yield list(zip(relation, status_combination))
答案 1 :(得分:1)
这个版本产生了更多连续的生成可能性,这是我从对话中理解的。我不知道这是否是你真正想要的。
from itertools import product
relations = ['grandfather', 'father', 'son']
statuses = ['tall', 'short']
possibilities = []
for per in range(1,4):
contiguous_relations = [relations[i: i+per] for i in range(-per+1+len(relations))]
possibilities.extend(contiguous_relations)
for possibility in possibilities:
print('---', possibility)
for p in product(statuses, repeat=len(possibility)):
print (list(zip(possibility, p)))
结果:
--- ['grandfather']
[('grandfather', 'tall')]
[('grandfather', 'short')]
--- ['father']
[('father', 'tall')]
[('father', 'short')]
--- ['son']
[('son', 'tall')]
[('son', 'short')]
--- ['grandfather', 'father']
[('grandfather', 'tall'), ('father', 'tall')]
[('grandfather', 'tall'), ('father', 'short')]
[('grandfather', 'short'), ('father', 'tall')]
[('grandfather', 'short'), ('father', 'short')]
--- ['father', 'son']
[('father', 'tall'), ('son', 'tall')]
[('father', 'tall'), ('son', 'short')]
[('father', 'short'), ('son', 'tall')]
[('father', 'short'), ('son', 'short')]
--- ['grandfather', 'father', 'son']
[('grandfather', 'tall'), ('father', 'tall'), ('son', 'tall')]
[('grandfather', 'tall'), ('father', 'tall'), ('son', 'short')]
[('grandfather', 'tall'), ('father', 'short'), ('son', 'tall')]
[('grandfather', 'tall'), ('father', 'short'), ('son', 'short')]
[('grandfather', 'short'), ('father', 'tall'), ('son', 'tall')]
[('grandfather', 'short'), ('father', 'tall'), ('son', 'short')]
[('grandfather', 'short'), ('father', 'short'), ('son', 'tall')]
[('grandfather', 'short'), ('father', 'short'), ('son', 'short')]