2

I have a list which has strings of length 1 up to n:

a = ['a','aq','thw','z']

I'm trying to obtain a flat list with only length 1 elements, expanding those the length of which is greater than 1. My current solution is:

l = []
for i in a:
    l = l + list(i)
print(l)
['a', 'a', 'q', 't', 'h', 'w', 'z']

Is there a more straight forward way of doing this avoiding a for loop?

My impression is that there might not be, however I'm curious where as to know if there is some other more efficient perhaps built-in method to accomplish this. Thanks in advance.

yatu
  • 86,083
  • 12
  • 84
  • 139
  • Because Python iterates over all iterables the same way, all of the answers from [How to make a flat list out of list of lists?](https://stackoverflow.com/questions/952914/how-to-make-a-flat-list-out-of-list-of-lists) should also work for you. – Patrick Haugh Dec 14 '18 at 15:27
  • 1
    Reopening for now. If anyone finds a better duplicate (there's likely to be one, I'm surprised this hasn't been asked before) then please ping me and I'll close again. – cs95 Dec 14 '18 at 15:46
  • I did give this a good search before asking. The fact that answers from other questions are valid to solve the problem does not make it a duplicate. – yatu Dec 14 '18 at 16:02

2 Answers2

6

This is the easiest way I can think to do it, with str.join + listification.

>>> list(''.join(a))
['a', 'a', 'q', 't', 'h', 'w', 'z']

There's also the solution with chain:

>>> from itertools import chain
>>> list(chain.from_iterable(a)) # Thanks, @Patrick Haugh!
['a', 'a', 'q', 't', 'h', 'w', 'z']

They're all pretty fast.

a2 = a * 100000
%timeit list(''.join(a2))
%timeit list(chain.from_iterable(a2))
%timeit [letter for word in a2 for letter in word]

11.1 ms ± 247 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)
32.3 ms ± 863 µs per loop (mean ± std. dev. of 7 runs, 10 loops each)
50.2 ms ± 1.3 ms per loop (mean ± std. dev. of 7 runs, 10 loops each)
cs95
  • 379,657
  • 97
  • 704
  • 746
3

Use a list comprehension:

>>> [letter for word in a for letter in word]
['a', 'a', 'q', 't', 'h', 'w', 'z']
Martin Frodl
  • 667
  • 4
  • 11