Создайте список с логическими значениями, которые представляют результаты предиката при применении к списку - PullRequest
1 голос
/ 07 июня 2011

Я пытаюсь выяснить, есть ли способ получить логический список путем сравнения в Python 3. В основном я хочу ввести следующее:

x = [1, 2, 3, 4, 5, 6, 7, 8, 9]
xlist = 4 <= x

и что я хочу вывести насписок, который выглядел бы так:

xlist = [False, False, False, True, True, True, True, True, True]

Есть ли способ сделать это просто без использования понимания списка, например

xlist = [4 <= i for i in x]

Есть ли что-нибудь, что было бы более эффективно с большими списками?

Ответы [ 6 ]

5 голосов
/ 07 июня 2011

Нет ничего плохого в понимании списка. Это как раз то, для чего были разработаны списки вещей.

Если вы используете NumPy (или SciPy), синтаксис, который вы ищете, действительно работает:

from numpy import array

...

x = array([1,2,3,4,5,6,7,8,9])
xlist = 4<=x

Но если у вас еще нет веской причины использовать NumPy, не стоит вводить его только для этого синтаксиса. В любом случае, если подумать, я не уверен, работает ли NumPy в Python 3.

4 голосов
/ 07 июня 2011

Необходимо учитывать, нужен ли вам промежуточный список или нет.Если нет, используйте вместо этого генераторное выражение .Например, all(i <= 4 for i in x) будет значительно быстрее и будет использовать меньше памяти, чем all([i <= 4 for i in x]).

2 голосов
/ 07 июня 2011

Карта скорее всего будет быстрее, но, , пожалуйста , профилируйте их, если вы действительно хотите знать.

Также рассмотрим модуль массива.

In [2]: %timeit map(lambda i: 4<=i, xrange(1,100))
100000 loops, best of 3: 15.9 us per loop

In [7]: %timeit list(4<=i for i in range(1,100))
100000 loops, best of 3: 10.3 us per loop

In [8]: %timeit list(4<=i for i in range(1,1000))
10000 loops, best of 3: 80.6 us per loop

In [10]: %timeit map(lambda i: 4<=i, xrange(1,1000))
10000 loops, best of 3: 155 us per loop
1 голос
/ 07 июня 2011

Вы также можете использовать следующее:

print map(lambda i: 4<=i, xrange(1,10))
1 голос
/ 07 июня 2011

Для больших списков это:

>>> (4<=i for i in range(1,10))
<generator object <genexpr> at 0xb75beedc>
>>> list(_)
[False, False, False, True, True, True, True, True, True]
# The list(_) is just to show what is inside the generator...

лучше чем:

>>> [4<=i for i in range(1,10)]
[False, False, False, True, True, True, True, True, True]

Насколько я понимаю, преимущество в скорости намного меньшек пониманию списка по сравнению с пониманием генератора в Python 3 по сравнению с Python 2. Этот синтаксис работает с обоими, и преимущество для большого списка одинаково: элементы списка генерируются сразу по сравнению с генератором, генерируемым по мере необходимости.

0 голосов
/ 07 июня 2011

Я думаю, вы уже делаете это правильно.

...