Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Python: find the first mismatch in two lists

Tags:

python

list

Given two lists of the same length, how could one efficiently find the first position where corresponding elements of these lists aren't equal? Basically I need either the index or the two unequal elements.

I'm interested if there exists some laconic "pythonic" solution, without obvious explicit iteration over the lists.

like image 660
Grigor Gevorgyan Avatar asked Apr 05 '13 09:04

Grigor Gevorgyan


1 Answers

You cannot avoid the iteration over the lists, but you can do it with a comprehension and obtain an elegant solution:

next( (idx, x, y) for idx, (x, y) in enumerate(zip(list1, list2)) if x!=y )

If you like something less one-line centric you can split it like this

coupled_idx = enumerate(zip(list1, list2))
res = next( idx for idx, (x, y) in coupled_idx if x!=y )

EDIT:

as addition, if you need to check the case where the two list can be completly equal, you can add a second parameter to the next function that tells it what return if no index has been found. The most common option is to return None:

coupled_idx = enumerate(zip(list1, list2))
res = next( (idx for idx, (x, y) in coupled_idx if x!=y), None )

Note that you need to enclose the generator expression between parenthesis because it's not the only argument of the function in this call.

Just to add a little fun, you can also ask the n-th different couple by chaining the expressions. For example this gives you all the couples up to the fifth one (filling with None if the couple is missing)

coupled_idx = enumerate(zip(list1, list2))
coupler = (idx for idx, (x, y) in coupled_idx if x!=y)
res = [ next(coupler, None) for _ in range(5) ]

EDIT2:

This kind of solution actually create a copy of both list via the zip function. If you need to avoid that you can use the function izip from the itertools module instead.

And about the fun part, you can select only certains solutions via the islice function fromt he same module

like image 89
EnricoGiampieri Avatar answered Sep 19 '22 19:09

EnricoGiampieri