Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Python: How to generate Full Factorial Combinations?

How can I use python to generate a full factorial of combinations? Is there a fancy itertools function that generates a full factorial?

I'm drawing a blank and can't think of another way to describe this other than "full factorial of combinations", so my search efforts have turned up with nothing relevant. What's the right terminology here? Search has turned up with combinations of certain lengths, but that's not what I'm after. The length is fixed by the number of factors.

Bonus: how to exclude certain combinations? how to do for arbitrary number of factors with arbitrary number of levels with the condition that the "levels" are not necessarily strings but any python object?

Let's say I have 5 factors, each with two or more levels. In this case I have 3 two-level factors and 2 three-level factors. The full factorial of combinations would have (2^3)*(3^2) = 8*9 = 72 combinations. Keep in mind that "L1" in X1 is different than "L1" in X2.

Input:

X1 = ["L1", "L2"]
X2 = ["L1", "L2", "L3"]
X3 = ["L1", "L2"]
X4 = ["L1", "L2"]
X5 = ["L1", "L2", "L3"]

full_factorial_combinations = itertools.fancyfunction(X1, X2, X3, X4, X5)
full_factorial_combinations #optionally produces a generator instead of list of tuples shown here

Output:

[("L1", "L1", "L1", "L1", "L1"),
("L1", "L1", "L1", "L1", "L2"),
("L1", "L1", "L1", "L1", "L3"),
("L1", "L1", "L1", "L2", "L1"),
("L1", "L1", "L1", "L2", "L2"),
("L1", "L1", "L1", "L2", "L3"),
("L1", "L1", "L2", "L1", "L1"),
("L1", "L1", "L2", "L1", "L2"),
("L1", "L1", "L2", "L1", "L3"),
("L1", "L1", "L2", "L2", "L1"),
("L1", "L1", "L2", "L2", "L2"),
("L1", "L1", "L2", "L2", "L3"),
("L1", "L2", "L1", "L1", "L1"),
("L1", "L2", "L1", "L1", "L2"),
("L1", "L2", "L1", "L1", "L3"),
("L1", "L2", "L1", "L2", "L1"),
("L1", "L2", "L1", "L2", "L2"),
("L1", "L2", "L1", "L2", "L3"),
("L1", "L2", "L2", "L1", "L1"),
("L1", "L2", "L2", "L1", "L2"),
("L1", "L2", "L2", "L1", "L3"),
("L1", "L2", "L2", "L2", "L1"),
("L1", "L2", "L2", "L2", "L2"),
("L1", "L2", "L2", "L2", "L3"),
("L1", "L3", "L1", "L1", "L1"),
("L1", "L3", "L1", "L1", "L2"),
("L1", "L3", "L1", "L1", "L3"),
("L1", "L3", "L1", "L2", "L1"),
("L1", "L3", "L1", "L2", "L2"),
("L1", "L3", "L1", "L2", "L3"),
("L1", "L3", "L2", "L1", "L1"),
("L1", "L3", "L2", "L1", "L2"),
("L1", "L3", "L2", "L1", "L3"),
("L1", "L3", "L2", "L2", "L1"),
("L1", "L3", "L2", "L2", "L2"),
("L1", "L3", "L2", "L2", "L3"),
("L2", "L1", "L1", "L1", "L1"),
("L2", "L1", "L1", "L1", "L2"),
("L2", "L1", "L1", "L1", "L3"),
("L2", "L1", "L1", "L2", "L1"),
("L2", "L1", "L1", "L2", "L2"),
("L2", "L1", "L1", "L2", "L3"),
("L2", "L1", "L2", "L1", "L1"),
("L2", "L1", "L2", "L1", "L2"),
("L2", "L1", "L2", "L1", "L3"),
("L2", "L1", "L2", "L2", "L1"),
("L2", "L1", "L2", "L2", "L2"),
("L2", "L1", "L2", "L2", "L3"),
("L2", "L2", "L1", "L1", "L1"),
("L2", "L2", "L1", "L1", "L2"),
("L2", "L2", "L1", "L1", "L3"),
("L2", "L2", "L1", "L2", "L1"),
("L2", "L2", "L1", "L2", "L2"),
("L2", "L2", "L1", "L2", "L3"),
("L2", "L2", "L2", "L1", "L1"),
("L2", "L2", "L2", "L1", "L2"),
("L2", "L2", "L2", "L1", "L3"),
("L2", "L2", "L2", "L2", "L1"),
("L2", "L2", "L2", "L2", "L2"),
("L2", "L2", "L2", "L2", "L3"),
("L2", "L3", "L1", "L1", "L1"),
("L2", "L3", "L1", "L1", "L2"),
("L2", "L3", "L1", "L1", "L3"),
("L2", "L3", "L1", "L2", "L1"),
("L2", "L3", "L1", "L2", "L2"),
("L2", "L3", "L1", "L2", "L3"),
("L2", "L3", "L2", "L1", "L1"),
("L2", "L3", "L2", "L1", "L2"),
("L2", "L3", "L2", "L1", "L3"),
("L2", "L3", "L2", "L2", "L1"),
("L2", "L3", "L2", "L2", "L2"),
("L2", "L3", "L2", "L2", "L3")]
like image 747
Kardo Paska Avatar asked Jan 22 '26 11:01

Kardo Paska


1 Answers

This is called the Cartesian product as implemented by itertools.product.

itertools.product(X1, X2, X3, X4, X5)
like image 183
Jared Goguen Avatar answered Jan 24 '26 00:01

Jared Goguen