Python: an elegant way to create a list of tuples?
>>> a=["a"]*4 >>> a ['a', 'a', 'a', 'a'] >>> b=range(4) >>> b [0, 1, 2, 3] >>> c = [range(4,8), range(9,13), range(14,18), range(19,23)] >>> c [[4, 5, 6, 7], [9, 10, 11, 12], [14, 15, 16, 17], [19, 20, 21, 22]] >>> >>> result = map(lambda x,y:[x,y],a,b) >>> map(lambda x,y:x.extend(y),result,c) >>> result = map(tuple, result) >>> result # desired output: [('a', 0, 4, 5, 6, 7), ('a', 1, 9, 10, 11, 12), ('a', 2, 14, 15, 16, 17), ('a', 3, 19, 20, 21, 22)] >>> >>> try_test = zip(a,b,c) >>> try_test # NOT DESIRED: leaves me with the list within the tuples [('a', 0, [4, 5, 6, 7]), ('a', 1, [9, 10, 11, 12]), ('a', 2, [14, 15, 16, 17]), ('a', 3, [19, 20, 21, 22])] I was wondering if anyone has a more concise way to make a “result”?
For a completely general approach to this problem, you can consider one of the many options on flatten , where you can find here where flatten is one that takes an arbitrary nested iterability of iterations and returns a flat list of the elements it contains.
Then just map the flatten to zipped values a, b, c and convert to a tuple.
>>> from collections import Iterable >>> def flatten(l): ... for i in l: ... if isinstance(i, Iterable) and not isinstance(i, basestring): ... for sub in flatten(i): ... yield sub ... else: ... yield i ... >>> map(tuple, map(flatten, zip(a, b, c))) [('a', 0, 4, 5, 6, 7), ('a', 1, 9, 10, 11, 12), ('a', 2, 14, 15, 16, 17), ('a', 3, 19, 20, 21, 22)] Or even more succinctly, modify flatten to accept an arbitrary list of arguments and return a tuple. Then you need map :
>>> def flat_tuple(*args): ... return tuple(flatten(args)) ... >>> map(flat_tuple, a, b, c) [('a', 0, 4, 5, 6, 7), ('a', 1, 9, 10, 11, 12), ('a', 2, 14, 15, 16, 17), ('a', 3, 19, 20, 21, 22)] If this is a one-time problem, the above approach is probably more of a problem than it's worth it. But if you have already defined flatten for other purposes, or if you often do this, then this can save a ton of problems!
Otherwise, just for fun, here is the nneonneo option to answer what I like:
>>> [x + tuple(y) for x, y in zip(zip(a, b), c)] [('a', 0, 4, 5, 6, 7), ('a', 1, 9, 10, 11, 12), ('a', 2, 14, 15, 16, 17), ('a', 3, 19, 20, 21, 22)]