Как извлечь элемент из набора с одним элементом в python?
Вопрос
Недавно я столкнулся со сценарием, в котором, если набор содержал только один элемент, я хотел что-то сделать с этим элементом.Чтобы получить элемент, я остановился на таком подходе:
element = list(myset)[0]
Но это не очень приятно, так как создает ненужный список.Это также можно было бы сделать с помощью итерации, но итерация также кажется неестественной, поскольку существует только один элемент.Я упускаю что-то простое?
Решение
Распаковка кортежей работает.
(element,) = myset
(Кстати, python-dev исследовал, но отклонил добавление myset.get ()
для возврата произвольного элемента из набора. Обсуждение здесь , Гвидо ван Россум отвечает 1 и 2 .)
Мой личный фаворит для получения произвольного элемента (если у вас есть неизвестное число, но также работает, если у вас есть только один):
element = next(iter(myset)) ¹
1 : в Python 2.5 и более ранних версиях вы должны использовать iter (myset) .next ()
Другие советы
Между созданием кортежа и созданием итератора это почти стирка, но итерация выигрывает носом ...:
$ python2.6 -mtimeit -s'x=set([1])' 'a=tuple(x)[0]'
1000000 loops, best of 3: 0.465 usec per loop
$ python2.6 -mtimeit -s'x=set([1])' 'a=tuple(x)[0]'
1000000 loops, best of 3: 0.465 usec per loop
$ python2.6 -mtimeit -s'x=set([1])' 'a=next(iter(x))'
1000000 loops, best of 3: 0.456 usec per loop
$ python2.6 -mtimeit -s'x=set([1])' 'a=next(iter(x))'
1000000 loops, best of 3: 0.456 usec per loop
Не уверен, почему во всех ответах используется более старый синтаксис iter (x) .next ()
, а не новый next (iter (x))
, который кажется предпочтительным для меня (а также работает в Python 3.1).
Однако распаковка выигрывает у обоих:
$ python2.6 -mtimeit -s'x=set([1])' 'a,=x'
10000000 loops, best of 3: 0.174 usec per loop
$ python2.6 -mtimeit -s'x=set([1])' 'a,=x'
10000000 loops, best of 3: 0.174 usec per loop
Это, конечно, для наборов из одного элемента (где последняя форма, как уже упоминалось, имеет преимущество быстрого отказа, если набор, о котором вы знали, имел только один элемент, в действительности имел несколько). Для множеств с произвольным N > 1 элементов, кортеж замедляется, а iter нет:
$ python2.6 -mtimeit -s'x=set(range(99))' 'a=next(iter(x))'
1000000 loops, best of 3: 0.417 usec per loop
$ python2.6 -mtimeit -s'x=set(range(99))' 'a=tuple(x)[0]'
100000 loops, best of 3: 3.12 usec per loop
Итак, распаковка для одиночного случая и next (iter (x))
для общего случая выглядят лучше всего.
Я считаю kaizer.se вот ответ это здорово.Но если ваш набор мог бы содержит более одного элемента, и вам нужен не такой уж произвольный элемент, который вы могли бы использовать min
или max
.Например.:
element = min(myset)
или:
element = max(myset)
(Не используйте sorted
, потому что это приводит к ненужным накладным расходам для данного использования.)
Я предлагаю:
element = myset.pop()
вы можете использовать element = tuple (myset) [0]
, что немного более эффективно, или вы можете сделать что-то вроде
element = iter(myset).next()
Я думаю, что создание итератора более эффективно, чем создание кортежа / списка.