Генерация всех комбинаций неизвестного числа переменных - PullRequest
0 голосов
/ 14 февраля 2020

У меня есть список переменных, количество которых может меняться. Каждая переменная имеет нижний предел, верхний предел и значение приращения. Например:

variables = {
   "a": [1, 10, 1],
   "b": [50, 200, 5],
   "c": [50, 300, 10]
}

Где для клавиши «a» 1 - нижний предел, 10 - верхний предел и 1 - величина приращения.

"a" would go from 1 through 10, incrementing by 1
"b" would go from 50 through 200, incrementing by 5
"c" would go from 50 through 300, incrementing by 10
... there can be more or less such keys.

Мне нужно создать список всех возможных комбинаций a, b и c, без жесткого кодирования вложенных циклов, поскольку существует неизвестное количество переменных / ключей, и я просто не могу обернуть его вокруг. Я использую Python 3.7

В идеале выводом будет таблица комбинаций каждой переменной, возможно, значений, разделенных запятыми. Например.

a  b  c
x  y  z
x  y  z
x  y  z
x  y  z

Тем не менее, все будет делать, пока я могу сопоставить вывод в формате, где каждая комбинация может быть доступна как набор. Например, список кортежей.

[
  (x, y, z)
  (x, y, z)
]
...

Ответы [ 4 ]

1 голос
/ 14 февраля 2020

Здесь, предполагая:

variables = {
   "a": [1, 10, 1],
   "b": [50, 200, 5],
   "c": [50, 300, 10]
}

Затем вы можете создать итератор, используя itertools:

from itertools import product, starmap
cartesian_product = product(*starmap(range, variables.values()))

Или просто показать вам, что делает starmap:

cartesian_product = product(*(range(*v) for v in variables.values()))
0 голосов
/ 14 февраля 2020

Попробуйте следующим образом:

var=[]
for k in variables.keys():
  var.append(np.arange(variables[k][0],variables[k][1]+1,variables[k][2]))

np.array(np.meshgrid(var[0],var[1],var[2])).T.reshape(-1,3)

для комбинации Я получил помощь от здесь

0 голосов
/ 14 февраля 2020

Вы можете использовать itertools :

import numpy as np
import itertools


a = np.arange(1, 10, 1)
b = np.arange(50, 200, 5)
c = np.arange(50,300,10)

results = itertools.product(a, b, c)
for item in results:
    print(item)

Выход:

(1, 50, 50)
(1, 50, 60)
...
...
(9, 195, 270)
(9, 195, 280)
(9, 195, 290)
0 голосов
/ 14 февраля 2020

Попробуйте:

import numpy as np
lst = [np.arange(v[0], v[1]+1, v[2]) for k,v in variables.items()]
np.array(np.meshgrid(*lst)).T.reshape(-1,len(lst))
...