Unpack list of lists into list [duplicate] - python

This question already has answers here:
How do I make a flat list out of a list of lists?
(34 answers)
Closed 4 years ago.
I have list of lists of tuples:
a = [[(1, 2), (3, 4), (5, 6)], [(7, 8), (9, 10)]]
How can I make one list of tuples:
b = [(1, 2), (3, 4), (5, 6), (7, 8), (9, 10)]
Naive way is:
b = []
for c in a:
for t in c:
b.append(t)
List comprehension or any other ideas are welcome.

Using itertools
demo:
import itertools
a = [[(1, 2), (3, 4), (5, 6)], [(7, 8), (9, 10)]]
print(list(itertools.chain(*a)))
Output:
[(1, 2), (3, 4), (5, 6), (7, 8), (9, 10)]

This operation is called 'flatten' in some of other languages.
In python, followings method might be shortest.
a = [[(1, 2), (3, 4), (5, 6)], [(7, 8), (9, 10)]]
sum(a, [])
// [(1, 2), (3, 4), (5, 6), (7, 8), (9, 10)]
It also work in the case the parent list have many child lists.
b = [[1],[2],[3],[4],[5]]
sum(b, [])
// [1, 2, 3, 4, 5]

You don't want to append, you want to extend. You can use the really simple loop
a = [[(1, 2), (3, 4), (5, 6)], [(7, 8), (9, 10)]]
single_level_list = []
for lst in a:
single_level_list.extend(lst)
print(single_level_list)
>>> [(1, 2), (3, 4), (5, 6), (7, 8), (9, 10)]

Related

All possible combinations of list elements in Python

I have a list B containing elements. I want to create all possible pairs using these elements as shown in the expected output. But I am getting an error. How do I fix it?
import numpy as np
import itertools
B=[ 1, 2, 5, 7, 10, 11]
combination=[]
for L in range(len(B) + 1):
for subset in itertools.combinations(B, L):
combination.append([list(sub) for sub in subset])
combination
The error is
in <listcomp>
combination.append([list(sub) for sub in subset])
TypeError: 'int' object is not iterable
The expected output is
[1,2],[1,5],[1,7],[1,10],[1,11],
[2,1],[2,5],[2,7],[2,10],[2,11],
[5,1],[5,2],[5,7],[5,10],[5,11],
[7,1],[7,2],[7,5],[7,10],[7,11],
[10,1],[10,2],[10,5],[10,7],[10,11],
[11,1],[11,2],[11,5],[11,7],[11,10]
What you are looking for is not combinations but permutations:
>>> list(itertools.permutations(B, 2))
[(1, 2),
(1, 5),
(1, 7),
(1, 10),
(1, 11),
(2, 1),
(2, 5),
(2, 7),
(2, 10),
(2, 11),
(5, 1),
(5, 2),
(5, 7),
(5, 10),
(5, 11),
(7, 1),
(7, 2),
(7, 5),
(7, 10),
(7, 11),
(10, 1),
(10, 2),
(10, 5),
(10, 7),
(10, 11),
(11, 1),
(11, 2),
(11, 5),
(11, 7),
(11, 10)]
To convert to a list:
# List comprehension
perm = [list(p) for p in itertools.permutations(B, 2)
# Functional programming
perm = list(map(list, itertools.permutations(B, 2)))
Beside the #Corralien answer which is the correct one, i am just correcting your solution to let you know that your solution can also be made to work just changing few things
Do not convert & iterate subset as it is already a list and its element is not iterable
Replace combinations with permutations
Add a condition to filter only two combinations as your code is producing permutation of N X N
Final version is following.
import numpy as np
import itertools
B=[ 1, 2, 5, 7, 10, 11]
combination=[]
for L in range(len(B) + 1):
for subset in itertools.permutations(B, L):
if len(subset) == 2:
combination.append(subset)
print(combination)
OUTPUT
[(1, 2), (1, 5), (1, 7), (1, 10), (1, 11), (2, 1), (2, 5), (2, 7), (2, 10), (2, 11), (5, 1), (5, 2), (5, 7), (5, 10), (5, 11), (7, 1), (7, 2), (7, 5), (7, 10), (7, 11), (10, 1), (10, 2), (10, 5), (10, 7), (10, 11), (11, 1), (11, 2), (11, 5), (11, 7), (11, 10)]

Itertools product return sets [duplicate]

This question already has answers here:
Cartesian products of lists without duplicates
(2 answers)
Closed 3 years ago.
I want to create an iterator with cartesian products where no duplicates are present in the sense of sets.
import itertools
A = list(range(1,10))
iterator = itertools.product(A,repeat=2)
print(list(iterator))
>> [(1,1),(1,2),...,(2,1),...,(9,9)]
Above is wrong in the sense that set((1,2)) == set((2,1)). I could do
B = list()
for i in iterator:
if all(set(i) != set(j) for j in B):
B.append(i)
and get a list of the wanted output, but I would like to stay away from lists since I run into memory problems when scaling the repeat-option.
Can anyone help me out?
A = list(range(1,10))
k = []
for i, v in enumerate(A):
for _, v1 in enumerate(A[i:]):
k.append((v, v1))
print(k)
Output is
[(1, 1), (1, 2), (1, 3), (1, 4), (1, 5), (1, 6), (1, 7), (1, 8), (1, 9), (2, 2), (2, 3), (2, 4), (2, 5), (2, 6), (2, 7), (2, 8), (2, 9), (3, 3), (3, 4), (3, 5), (3, 6), (3, 7), (3, 8), (3, 9), (4, 4), (4, 5), (4, 6), (4, 7), (4, 8), (4, 9), (5, 5), (5, 6), (5, 7), (5, 8), (5, 9), (6, 6), (6, 7), (6, 8), (6, 9), (7, 7), (7, 8), (7, 9), (8, 8), (8, 9), (9, 9)]

Checking if the numbers in a list in a list are in a certain range

So I have a list with multiple list in it which represent something like coordinates. In my case they are positions on a chessboard.
The list would look something like this:
[(3, 3), (4, 3), (5, 3), (6, 3), (3, 4), (4, 4), (5, 4), (6, 4), (3, 5), (4, 5)]
This is just an example.
My problem is, I need to check if any of these coordiantes are out of a certain range, on the chessboard, for example 1-8. Unfortunately i could only get the all() command to work with a list which just consists of numbers and not a list with lists of numbers.
Then iterate through each of the individual coordinates:
>>> coords = [(3, 3), (4, 3), (5, 3), (6, 3), (3, 4), (4, 4), (5, 4), (6, 4), (3, 5), (4, 5)]
>>> all(1 <= c <= 8 for coord in coords for c in coord)
True
Let's try two cases where there is a coordinate out of range:
>>> coords = [(3, 3), (4, 3), (5, 3), (6, 3), (3, 4), (0, 5), (4, 4), (5, 4), (6, 4), (3, 5), (4, 5)]
>>> all(1 <= c <= 8 for coord in coords for c in coord)
False
>>> coords = [(3, 3), (4, 3), (5, 3), (6, 3), (4, 88), (3, 4), (4, 4), (5, 4), (6, 4), (3, 5), (4, 5)]
>>> all(1 <= c <= 8 for coord in coords for c in coord)
False
you can import numpy module and use function max
import numpy as np
>>> l =np.array([(3, 3), (4, 3), (5, 3), (6, 3), (3, 4), (4, 4), (5, 4), (6, 4), (3, 5), (4, 5)])
>>> l.max()
6

Generating pairs from python list

I'm trying generate a bunch of pairs from a list in python --- I figured out a way of doing it using for loops:
keys = range(10)
keypairs = list()
for i in range(len(keys)):
for j in range(i+1, len(keys)):
keypairs = keypairs + [(keys[i], keys[j])]
Is there a more "python style" way of doing this? My method doesn't seem very elegant ...
You want two range loops, one from 0 to n and the inner from each i of the first range + 1 to n using a list comp:
n = 10
pairs = [(i, j) for i in range(n) for j in range(i+1, n)]
from pprint import pprint as pp
pp(pairs,compact=True)
[(0, 1), (0, 2), (0, 3), (0, 4), (0, 5), (0, 6), (0, 7), (0, 8), (0, 9), (1, 2),
(1, 3), (1, 4), (1, 5), (1, 6), (1, 7), (1, 8), (1, 9), (2, 3), (2, 4), (2, 5),
(2, 6), (2, 7), (2, 8), (2, 9), (3, 4), (3, 5), (3, 6), (3, 7), (3, 8), (3, 9),
(4, 5), (4, 6), (4, 7), (4, 8), (4, 9), (5, 6), (5, 7), (5, 8), (5, 9), (6, 7),
(6, 8), (6, 9), (7, 8), (7, 9), (8, 9)]
Which exactly matches your output.
You want to check list comprehension:
sorted([(i, j) for j in range(10) for i in range(10) if j > i])
I would use itertools for that. Check combinations_with_replacement and combinations methods.
And here is the code sample:
import itertools
list(itertools.combinations(keys, 2))
EDITED: Yes, I noticed that it should be combinations, not combinations_with_replacements.

Making Combinations (Python)

In Python, is there a better way to get the set of combinations of n elements from a k-element set than nested for loops or list comprehensions?
For example, say from the set [1,2,3,4,5,6] I want to get [(1,2),(1,3),(1,4),(1,5),(1,6),(2,3),(2,4),(2,5),(2,6),(3,4),(3,5),(3,6),(4,5),(4,6),(5,6)]. Is there a better of of making it than
nums=[1,2,3,4,5,6]
doubles=[]
for a in nums:
for b in nums[a+1:]
doubles.append((a,b))
? It's okay if the elements of the list we end up with are sets, tuples, or lists; I just feel there should be an easier way to do this.
You can use itertools.combinations:
>>> from itertools import combinations
>>> nums = [1,2,3,4,5,6]
>>> list(combinations(nums, 2))
[(1, 2), (1, 3), (1, 4), (1, 5), (1, 6), (2, 3), (2, 4), (2, 5), (2, 6), (3, 4), (3, 5), (3, 6), (4, 5), (4, 6), (5, 6)]
The itertools module has a lot of really powerful tools that can be used in situations like this. In this case, you want itertools.combinations. Some other ones that you might find useful are itertools.combinations_with_replacement and itertools.permutations.
Example:
>>> import itertools
>>> list(itertools.combinations(range(1,7),2))
[(1, 2), (1, 3), (1, 4), (1, 5), (1, 6), (2, 3), (2, 4), (2, 5), (2, 6), (3, 4), (3, 5), (3, 6), (4, 5), (4, 6), (5, 6)]
>>> list(itertools.combinations_with_replacement(range(1,7),2))
[(1, 1), (1, 2), (1, 3), (1, 4), (1, 5), (1, 6), (2, 2), (2, 3), (2, 4), (2, 5), (2, 6), (3, 3), (3, 4), (3, 5), (3, 6), (4, 4), (4, 5), (4, 6), (5, 5), (5, 6), (6, 6)]
>>> list(itertools.permutations(range(1,7),2))
[(1, 2), (1, 3), (1, 4), (1, 5), (1, 6), (2, 1), (2, 3), (2, 4), (2, 5), (2, 6), (3, 1), (3, 2), (3, 4), (3, 5), (3, 6), (4, 1), (4, 2), (4, 3), (4, 5), (4, 6), (5, 1), (5, 2), (5, 3), (5, 4), (5, 6), (6, 1), (6, 2), (6, 3), (6, 4), (6, 5)]
You could use the itertools module
import itertools
alphabet = ['1','2','3','4','5','6']
combos = list(itertools.combinations(alphabet, 2))
print combos

Categories

Resources