Pythonic способ сравнить два списка и распечатать различия

У меня есть два списка, которые гарантированно имеют одинаковую длину. Я хочу сравнить соответствующие значения в списке (кроме первого элемента) и распечатать те, которые не совпадают. То, как я это делаю, похоже на это

i = len(list1)
if i == 1:
    print 'Nothing to compare'
else:
    for i in range(i):
        if not (i == 0):
            if list1[i] != list2[i]:
                print list1[i]
                print list2[i]

Есть ли лучший способ сделать это? (Python 2.x)

Ответы

Ответ 1

list1=[1,2,3,4]
list2=[1,5,3,4]
print [(i,j) for i,j in zip(list1,list2) if i!=j]

Вывод:

[(2, 5)]

Изменить: Легко расширяется, чтобы пропускать n первых элементов (тот же вывод):

list1=[1,2,3,4]
list2=[2,5,3,4]
print [(i,j) for i,j in zip(list1,list2)[1:] if i!=j]

Ответ 2

Никто не упоминает фильтр:

a = [1, 2, 3]
b = [42, 3, 4]

aToCompare = a[1:]
bToCompare = b[1:]

c = filter( lambda x: (not(x in aToCompare)), bToCompare)
print c

Ответ 3

edit: oops, не видел часть "игнорировать первый элемент"

from itertools import islice,izip

for a,b in islice(izip(list1,list2),1,None):
    if a != b:
       print a, b

Ответ 4

В стандартной библиотеке для этого есть класс difflib.SequenceMatcher.

Ответ 5

Отмечая требование пропустить первую строку:

from itertools import izip
both = izip(list1,list2)
both.next()  #skip the first
for p in (p for p in both if p[0]!=p[1]):
   print pair
  1. Здесь используется izip, итератор (itertools) версии zip, чтобы сгенерировать итератор через пары значений. Таким образом, вы не используете загрузку памяти, генерируя полный список.
  2. Он обрабатывает итератор both на единицу, чтобы избежать обработки первого элемента, и избегать необходимости делать сравнение индексов на каждом шаге через цикл. Это также делает его более чистым для чтения.
  3. Наконец, он проходит через каждый кортеж, возвращенный из генератора, который дает только неравные пары.

Ответ 6

Вы можете использовать наборы:

>>> list1=[1,2,3,4]
>>> list2=[1,5,3,4]
>>> set(list1[1:]).symmetric_difference(list2[1:])
set([2, 5])

Ответ 7

Предполагая, что два типа равны и имеют одинаковую длину:

list1=[1,2,3,4]
list2=[1,5,3,4]
print list1==list2

Ответ 8

Вы можете использовать set operation чтобы найти симметричную разницу (^) между двумя списками. Это один из лучших питоновских способов сделать это.

list1=[1,2,3,4]
list2=[1,5,3,4]

print(set(list1) ^ set(list2))

Таким образом, результат будет {2, 5}