我试图编写一个算法来生成 a 大小的列表列表,其中任何 b 的联合列表数量包含所有列表中显示的数字集。此外,没有b - 1数量的列表应包含出现在所有列表中的数字集......
a 可以介于1-9和 b 之间,可以介于0-9之间。
示例:
a = 3
b = 2
回答= [[0,1],[0,2],[1,2]]
我需要三个列表,其中任何2个列表的联合包含[0,1,2]。
我到目前为止所做的是编写两个函数,一个检查列表是否符合条件并返回一个布尔值,另一个生成组合直到满足条件(非常低效,仅在b&lt时有效) ; 3)。
from itertools import combinations
# Checks if an answer is successful
def check(answer, b):
# get set of total keys
answer_set = []
answer_set.extend([i for l in answer for i in l])
answer_set = set(answer_set)
# Check if all combinations of b size hold
for target in combinations(answer, b):
test = set([i for l in target for i in l])
if not answer_set.issubset(test):
return False
# Check if it doesn't hold for b - 1
for fail in combinations(answer, b - 1):
test = set([i for l in fail for i in l])
if answer_set.issubset(test):
return False
# Return True if all tests were passed
return True
# Brute force all combinations
def brute(a, b, answer=1):
# Establish set of numbers to try
test_set = set(range(answer))
# Test if set of numbers contains a passing answer
for attempt in range(10):
test_set.add(len(test_set))
set_combo = combinations(test_set, attempt)
for combo in combinations(set_combo, a):
if check(combo, b):
return combo
return brute(a, b, answer + 1)
如果我输入的内容正确,我们应该有代码回答上面的例子(尽管我相信它会返回一个元组元组,但现在这并不重要)。注意:有些特殊情况我的暴力无法解决,例如a == b。
显然,蛮力不会在更大尺寸上工作,因为可能的组合数量变得疯狂处理。我需要一种新方法......
我前进的想法是确定a和b之间的特殊关系,这样我就可以计算出联合是出现在所有集合中的数字集合的可能组合的数量。我可以从a和b中收集任何信息来获取列表的大小以及每个项目的可能数值,这将是我的下一个猜测。
无论如何,任何帮助都表示赞赏。
编辑:联盟,而不是交集。