Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Iterating over two lists one after another

Tags:

I have two lists list1 and list2 of numbers, and I want to iterate over them with the same instructions. Like this:

for item in list1:   print(item.amount)   print(item.total_amount)  for item in list2:   print(item.amount)   print(item.total_amount) 

But that feels redundant. I know I can write for item in list1 + list2:, but it has a price of running-time.

Is there a way do that without loose time?

like image 736
zardav Avatar asked Feb 04 '16 15:02

zardav


People also ask

Can you loop through 2 lists in Python?

Use the izip() Function to Iterate Over Two Lists in Python It iterates over the lists until the smallest of them gets exhausted. It then zips or maps the elements of both lists together and returns an iterator object. It returns the elements of both lists mapped together according to their index.

Can you iterate over lists?

Iterating over a list can also be achieved using a while loop. The block of code inside the loop executes until the condition is true. A loop variable can be used as an index to access each element.


2 Answers

This can be done with itertools.chain:

import itertools  l1 = [1, 2, 3, 4] l2 = [5, 6, 7, 8]  for i in itertools.chain(l1, l2):     print(i, end=" ") 

Which will print:

1 2 3 4 5 6 7 8  

As per the documentation, chain does the following:

Make an iterator that returns elements from the first iterable until it is exhausted, then proceeds to the next iterable, until all of the iterables are exhausted.

If you have your lists in a list, itertools.chain.from_iterable is available:

l = [l1, l2] for i in itertools.chain.from_iterable(l):     print(i, end=" ") 

Which yields the same result.

If you don't want to import a module for this, writing a function for it is pretty straight-forward:

def custom_chain(*it):     for iterab in it:         yield from iterab 

This requires Python 3, for Python 2, just yield them back using a loop:

def custom_chain(*it):     for iterab in it:         for val in iterab:             yield val 

In addition to the previous, Python 3.5 with its extended unpacking generalizations, also allows unpacking in the list literal:

for i in [*l1, *l2]:     print(i, end=" ") 

though this is slightly faster than l1 + l2 it still constructs a list which is then tossed; only go for it as a final solution.

like image 63
Dimitris Fasarakis Hilliard Avatar answered Sep 20 '22 12:09

Dimitris Fasarakis Hilliard


chain works, but if you feel that it's overkill to import a module just to call a single function once, you can replicate its behavior inline:

for seq in (list1, list2):   for item in seq:     print(item.amount)     print(item.total_amount) 

Creating the (list1, list2) tuple is O(1) with respect to list length, so it should perform favorably in comparison to concatenating the lists together.

like image 40
Kevin Avatar answered Sep 18 '22 12:09

Kevin