Esistono diversi eleganti esempi di utilizzo di numpy in Python per generare matrici di tutte le combinazioni. Ad esempio la risposta qui: Using numpy to build an array of all combinations of two arrays.Generazione di una matrice numpy con tutte le combinazioni di numeri che sommano a meno di un dato numero
Supponiamo ora che ci sia un vincolo in più, vale a dire che la somma di tutti i numeri non può sommare più di una determinata costante K
. Utilizzando un generatore e itertools.product
, per un esempio con K=3
dove vogliamo le combinazioni di tre variabili con campi di 0-1,0-3, 0-2 e lo possiamo fare una segue:
from itertools import product
K = 3
maxRange = np.array([1,3,2])
states = np.array([i for i in product(*(range(i+1) for i in maxRange)) if sum(i)<=K])
che restituisce
array([[0, 0, 0],
[0, 0, 1],
[0, 0, 2],
[0, 1, 0],
[0, 1, 1],
[0, 1, 2],
[0, 2, 0],
[0, 2, 1],
[0, 3, 0],
[1, 0, 0],
[1, 0, 1],
[1, 0, 2],
[1, 1, 0],
[1, 1, 1],
[1, 2, 0]])
In linea di principio, l'approccio da https://stackoverflow.com/a/25655090/1479342 può essere utilizzato per generare tutte le possibili combinazioni senza il vincolo e quindi selezionando il sottoinsieme di combinazioni che riassumono a meno di K
. Tuttavia, questo approccio genera molte più combinazioni del necessario, specialmente se K
è relativamente piccolo rispetto a sum(maxRange)
.
Ci deve essere un modo per farlo più velocemente e con un minor utilizzo di memoria. Come può essere realizzato utilizzando un approccio vettoriale (ad esempio utilizzando np.indices
)?
Tecnicamente , questi sono sottoinsiemi di un (multi) set, non di combinazioni. – blazs
È sempre il caso che l'intervallo di valori possibili nella posizione k sia 0..Nk, o la soluzione deve considerare insiemi arbitrari di valori possibili in ogni posizione? – cxrodgers
@cxrodgers Una soluzione per la situazione con 0 ... Nk sarebbe grandiosa. Una soluzione in cui gli intervalli di 'k' saranno' np.arange (minRange [k], maxRange [k] +1) 'sarebbe ancora meglio, ma questo può essere derivato direttamente dalla prima soluzione se non mi sbaglio . Con insiemi arbitrari questo sarebbe complicato dal momento che c'è una piccola struttura che può essere sfruttata. – Forzaa