我有两个清单
[1, 3, 4] [7, 8]
我想从最小的组合开始生成两个列表的所有组合,例如17,18,37,38,47,48,137,138,147,148......178,378.... Now,对于每个组合,我必须测试它是否存在于其他地方,如果我发现该组合存在,那么我将停止组合生成。例如,如果我看到17存在,那么我将不会生成其他组合。再说一次,如果发现48我在场,那么我将不会生成以后的组合。
17,18,37,38,47,48,137,138,147,148......178,378....
17
48
这是一个非常丑陋的算法,但是对我有用。它也不是超级昂贵的(当然,期望使用itertools.combinations(a,i)生成所有组合):
import itertools def all_combs(a): to_return = [] temp = [] for i in a: temp.append(i) to_return.append(temp) for i in range(2, len(a) + 1): temp = [] for j in itertools.combinations(a, i): s = "" for k in j: s = s + str(k) temp.append(int(s)) #Get all values from the list permutation to_return.append(temp) print(to_return) return to_return def all_perm(a, b): a_combs = all_combs(a) b_combs = all_combs(b) to_return = [] for i in a_combs: for j in b_combs: for k in i: for l in j: to_return.append(10**len(str(l)) * k + l) to_return.sort() for i in to_return: yield i
编辑:修复了无法正确读取多位数字值的错误编辑:使函数充当了生成器编辑:修复了涉及数字的错误(通过添加排序…)
编辑:这是一个非常出色的实现,可以更紧密地满足生成器样式。它仍然不是完美的,但是在一般情况下应该可以提供良好的加速效果:
import itertools def add_to_dict(dict, length, num): if not length in dict: dict[length] = [] dict[length].append(num) def sum_to_val(val): to_return = [] for i in range(1, val): to_return.append([i, val-i]) return to_return def all_combs(a): to_return = {} for i in a: add_to_dict(to_return, len(str(i)), i) for i in range(2, len(a) + 1): for j in itertools.combinations(a, i): s = "" for k in j: s = s + str(k) add_to_dict(to_return, len(s), int(s)) #Get all values from the list permutation return to_return def all_perm(a, b): a_combs = all_combs(a) b_combs = all_combs(b) for val in range(max(a_combs.keys())+max(b_combs.keys())+1): to_return = [] sums = sum_to_val(val) for i in sums: if not(i[0] in a_combs and i[1] in b_combs): continue for j in a_combs[i[0]]: for k in b_combs[i[1]]: to_return.append(10**len(str(k)) * j + k) to_return.sort() for i in to_return: yield i