Python за допомогою перерахування розуміння списку всередині списку


125

Припустимо, у мене є такий список:

mylist = ["a","b","c","d"]

Щоб отримати значення, надруковані разом з їх індексом, я можу використовувати enumerateфункцію Python, як це

>>> for i,j in enumerate(mylist):
...     print i,j
...
0 a
1 b
2 c
3 d
>>>

Тепер, коли я намагаюся використовувати його всередині, list comprehensionце дає мені цю помилку

>>> [i,j for i,j in enumerate(mylist)]
  File "<stdin>", line 1
    [i,j for i,j in enumerate(mylist)]
           ^
SyntaxError: invalid syntax

Отже, моє запитання: який правильний спосіб використання перерахування всередині списку?

Відповіді:


166

Спробуйте це:

[(i, j) for i, j in enumerate(mylist)]

Вам потрібно покласти i,jвсередині кордону, щоб зрозуміти список. Крім того, враховуючи, що enumerate() вже повертається кортеж, ви можете повернути його безпосередньо, не розпаковуючи його спочатку:

[pair for pair in enumerate(mylist)]

У будь-якому випадку результат, який повертається, як очікується:

> [(0, 'a'), (1, 'b'), (2, 'c'), (3, 'd')]

4
Не обов’язково бути кортежем. Будь-який вираз із використанням i та j, який повертає значення, зробить
Альваро,

використання перерахування чудово, як щодо підвищення ефективності використання itertools
Pramit

3
Просто пам’ятайте, що кортеж будується , не the (). Тож "класти i,jвсередину кортежу" не має сенсу, оскільки i,jце вже кортеж! Проблема полягає в тому, що аналізатору списку потрібні паролі для групи операторів.
коубер

46

Щоб бути дійсно зрозумілим, це не має нічого спільного enumerateі все пов'язане з синтаксисом розуміння списку.

Це розуміння списку повертає список кортежів:

[(i,j) for i in range(3) for j in 'abc']

це список диктів:

[{i:j} for i in range(3) for j in 'abc']

список списків:

[[i,j] for i in range(3) for j in 'abc']

помилка синтаксису:

[i,j for i in range(3) for j in 'abc']

Що є непослідовним (IMHO) і плутає з синтаксисом розуміння словника:

>>> {i:j for i,j in enumerate('abcdef')}
{0: 'a', 1: 'b', 2: 'c', 3: 'd', 4: 'e', 5: 'f'}

І набір кортежів:

>>> {(i,j) for i,j in enumerate('abcdef')}
set([(0, 'a'), (4, 'e'), (1, 'b'), (2, 'c'), (5, 'f'), (3, 'd')])

Як заявив Оскар Лопес, ви можете просто передати перелічений кортеж безпосередньо:

>>> [t for t in enumerate('abcdef') ] 
[(0, 'a'), (1, 'b'), (2, 'c'), (3, 'd'), (4, 'e'), (5, 'f')]

32

Або, якщо ви не наполягаєте на використанні розуміння списку:

>>> mylist = ["a","b","c","d"]
>>> list(enumerate(mylist))
[(0, 'a'), (1, 'b'), (2, 'c'), (3, 'd')]

12

Якщо ви користуєтесь довгими списками, це розуміння списку швидше, не кажучи вже про більш читабельному.

~$ python -mtimeit -s"mylist = ['a','b','c','d']" "list(enumerate(mylist))"
1000000 loops, best of 3: 1.61 usec per loop
~$ python -mtimeit -s"mylist = ['a','b','c','d']" "[(i, j) for i, j in enumerate(mylist)]"
1000000 loops, best of 3: 0.978 usec per loop
~$ python -mtimeit -s"mylist = ['a','b','c','d']" "[t for t in enumerate(mylist)]"
1000000 loops, best of 3: 0.767 usec per loop

2
+1 Я цього не тестував, але ставлю [t for t in enumerate(my list)]ще швидше.
вовк

11

Ось спосіб це зробити:

>>> mylist = ['a', 'b', 'c', 'd']
>>> [item for item in enumerate(mylist)]
[(0, 'a'), (1, 'b'), (2, 'c'), (3, 'd')]

Крім того, ви можете:

>>> [(i, j) for i, j in enumerate(mylist)]
[(0, 'a'), (1, 'b'), (2, 'c'), (3, 'd')]

Причиною виникнення помилки було те, що ви пропустили () навколо iта jзробити його кортежем.



0

Всі чудові відповіді, хлопці. Я знаю, що питання тут є специфічним для перерахування, але як щодо такого подібного, просто іншого погляду

from itertools import izip, count
a = ["5", "6", "1", "2"]
tupleList = list( izip( count(), a ) )
print(tupleList)

Він стає більш потужним, якщо доводиться паралельно повторювати кілька списків з точки зору продуктивності. Просто думка

a = ["5", "6", "1", "2"]
b = ["a", "b", "c", "d"]
tupleList = list( izip( count(), a, b ) )
print(tupleList)
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.