1

Not a particularly complex question but I'm looking for a efficient/clean way to generate all possible permutations of tuples.

For example, given a size value (ex. 3) for an n x n grid.

(1,1) (2,1) (3,1)
(1,2) (2,2) (3,2)
(1,3) (2,3) (3,3)

I'd like to generate comparisons between rows and columns.

So for rows, comparisons would go as (1,1) vs (2,1), (1,1) vs (3,1), (2,1) vs (3,1) ... (1,2) vs (2,2), (2,2) vs (3,2) ... etc

And for columns, comparisons would go as (1,1) vs (1,2), (1,1) vs (1,3), (1,2) vs (1,3), .. (2,1) vs (2,2), (2,1) vs (2,3), (2,2) vs (2,3) ... etc

Does anyone know of an easy way to generate each pair of tuples? I'd like to pass the two tuples from the comparison into a separate function (tuple1, tuple2). Got an idea but it uses multiple for loops and seems inefficient. Assistance would be appreciated.

Thierry Lathuille
  • 23,663
  • 10
  • 44
  • 50
SS'
  • 819
  • 1
  • 8
  • 18

1 Answers1

2

Using itertools.combinations, you can generate all combinations of 2 indices without repetition.

So, you can generate your pairs of tuples like this:

from itertools import combinations

def columns(n):
    for j in range(1, n+1):
        for i1, i2 in combinations(range(1, n+1), 2):
            yield ((i1, j), (i2, j))

def lines(n):
    for i in range(1, n+1):
        for j1, j2 in combinations(range(1, n+1), 2):
            yield ((i, j1), (i, j2))

n = 3
print(list(columns(n)))
print(list(lines(n)))

# [((1, 1), (2, 1)), ((1, 1), (3, 1)), ((2, 1), (3, 1)), ((1, 2), (2, 2)), ((1, 2), (3, 2)), ((2, 2), (3, 2)), ((1, 3), (2, 3)), ((1, 3), (3, 3)), ((2, 3), (3, 3))]
# [((1, 1), (1, 2)), ((1, 1), (1, 3)), ((1, 2), (1, 3)), ((2, 1), (2, 2)), ((2, 1), (2, 3)), ((2, 2), (2, 3)), ((3, 1), (3, 2)), ((3, 1), (3, 3)), ((3, 2), (3, 3))]

And use them like:

for tuple1, tuple2 in lines(n):
    your_function(tuple1, tuple2)
Thierry Lathuille
  • 23,663
  • 10
  • 44
  • 50