list.append()
является очевидным выбором для добавления в конец списка. Вот разумное объяснение пропавшего без вести list.prepend()
. Предполагая, что мой список короткий и проблемы с производительностью незначительны, это
list.insert(0, x)
или
list[0:0] = [x]
идиоматическое?
Если вы можете пойти функциональным путем, следующее довольно ясно
Конечно , вы не вставили
x
вyour_list
, а вы создали новый список сx
preprended к нему.источник
Обычно вы не хотите повторяться перед списком в Python.
Если это коротко , и вы не делаете это много ... тогда хорошо.
list.insert
list.insert
Можно использовать таким образом.Но это неэффективно, потому что в Python a
list
является массивом указателей, и Python должен теперь взять каждый указатель в списке и переместить его вниз на единицу, чтобы вставить указатель на ваш объект в первом слоте, так что это действительно только эффективно для довольно коротких списков, как вы просите.Вот фрагмент из источника CPython, где это реализовано - и, как вы можете видеть, мы начинаем с конца массива и перемещаем все вниз на единицу для каждой вставки:
Если вам нужен контейнер / список, эффективный для добавления элементов, вам нужен связанный список. Python имеет двусвязный список, который можно быстро вставить в начало и в конец - он называется a
deque
.deque.appendleft
А
collections.deque
имеет много методов списка.list.sort
исключение, делающееdeque
окончательно не полностью заменяемым Лисковаlist
.deque
Также имеетappendleft
метод (а такжеpopleft
). Этоdeque
двусторонняя очередь и двусвязный список - независимо от длины, всегда требуется одинаковое количество времени для предварительной подготовки чего-либо. В больших обозначениях O время O (1) и время O (n) для списков. Вот использование:deque.extendleft
Также актуален метод deque
extendleft
, который итеративно добавляет:Обратите внимание, что каждый элемент будет добавляться по одному за раз, таким образом, эффективно изменяя их порядок.
Производительность
list
противdeque
Сначала мы настроим итеративное добавление:
и производительность:
Deque намного быстрее. Поскольку списки становятся длиннее, я ожидаю, что deque будет работать еще лучше. Если вы можете использовать deque,
extendleft
вы, вероятно, получите лучшую производительность таким образом.источник
Если кто-то найдет этот вопрос, как я, вот мои тесты производительности предлагаемых методов:
Как видите,
insert
и назначение среза почти в два раза быстрее, чем явное добавление, и результаты очень близки. Как отметил Рэймонд Хеттингер,insert
это более распространенный вариант, и я лично предпочитаю использовать этот способ для добавления в список.источник
.insert
и[0:0] = [0]
работают на месте , им все равно приходится перераспределять весь буфер.