Вопрос-Ответ

How to remove an element from a list by index

Как удалить элемент из списка по индексу

Как мне удалить элемент из списка по индексу?

Я нашел list.remove(), но это медленно сканирует список на предмет элемента по значению.

Переведено автоматически
Ответ 1

Используйте del и укажите индекс элемента, который вы хотите удалить:

>>> a = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
>>> del a[-1]
>>> a
[0, 1, 2, 3, 4, 5, 6, 7, 8]

Также поддерживает фрагменты:

>>> del a[2:4]
>>> a
[0, 1, 4, 5, 6, 7, 8, 9]

Здесь приведен раздел из руководства.

Ответ 2

Вы, вероятно, хотите pop:

a = ['a', 'b', 'c', 'd']
a.pop(1)

# now a is ['a', 'c', 'd']

По умолчанию, pop без каких-либо аргументов удаляет последний элемент:

a = ['a', 'b', 'c', 'd']
a.pop()

# now a is ['a', 'b', 'c']
Ответ 3

Как и другие упомянутые, pop и del являются эффективными способами удаления элемента с заданным индексом. Но только ради завершения (поскольку то же самое можно сделать многими способами в Python):

Использование фрагментов (это не выполняется при удалении элемента из исходного списка):

(Также это будет наименее эффективный метод при работе со списком Python, но это может быть полезно (но, повторяю, неэффективно) при работе с определяемыми пользователем объектами, которые не поддерживают pop, но определяют a __getitem__ ):

>>> a = [1, 2, 3, 4, 5, 6]
>>> index = 3 # Only positive index

>>> a = a[:index] + a[index+1 :]
# a is now [1, 2, 3, 5, 6]

Примечание: Пожалуйста, обратите внимание, что этот метод не изменяет список на месте, как pop и del. Вместо этого он создает две копии списков (одну от начала до индекса, но без него (a[:index]) и одну после индекса до последнего элемента (a[index+1:])) и создает новый объект list, добавляя оба. Затем он переназначается переменной list (a). Следовательно, разыменовывается старый объект list и, следовательно, собирается мусор (при условии, что на исходный объект list не ссылается никакая переменная, кроме a ).

Это делает этот метод очень неэффективным, а также может приводить к нежелательным побочным эффектам (особенно когда другие переменные указывают на исходный объект списка, который остается неизмененным).

Спасибо @MarkDickinson за указание на это ...

Этот ответ Stack Overflow объясняет концепцию нарезки.

Также обратите внимание, что это работает только с положительными индексами.

При использовании с объектами должен быть определен __getitem__ метод и, что более важно, __add__ метод должен быть определен для возврата объекта, содержащего элементы из обоих операндов.

По сути, это работает с любым объектом, определение класса которого похоже:

class foo(object):
def __init__(self, items):
self.items = items

def __getitem__(self, index):
return foo(self.items[index])

def __add__(self, right):
return foo( self.items + right.items )

Это работает с методами list которые определяют __getitem__ и __add__.

Сравнение трех способов с точки зрения эффективности:

Предположим, что предварительно определено следующее:

a = range(10)
index = 3

Метод del object[index]:

На сегодняшний день это самый эффективный метод. Он работает со всеми объектами, которые определяют __del__ метод.

Дизассемблирование выглядит следующим образом:

Код:

def del_method():
global a
global index
del a[index]

Дизассемблирование:

 10    0 LOAD_GLOBAL     0 (a)
3 LOAD_GLOBAL 1 (index)
6 DELETE_SUBSCR # This is the line that deletes the item
7 LOAD_CONST 0 (None)
10 RETURN_VALUE
None

pop метод:

Он менее эффективен, чем метод del, и используется, когда вам нужно получить удаленный элемент.

Код:

def pop_method():
global a
global index
a.pop(index)

Дизассемблирование:

 17     0 LOAD_GLOBAL     0 (a)
3 LOAD_ATTR 1 (pop)
6 LOAD_GLOBAL 2 (index)
9 CALL_FUNCTION 1
12 POP_TOP
13 LOAD_CONST 0 (None)
16 RETURN_VALUE

Метод slice and add .

Наименее эффективный.

Код:

def slice_method():
global a
global index
a = a[:index] + a[index+1:]

Дизассемблирование:

 24     0 LOAD_GLOBAL    0 (a)
3 LOAD_GLOBAL 1 (index)
6 SLICE+2
7 LOAD_GLOBAL 0 (a)
10 LOAD_GLOBAL 1 (index)
13 LOAD_CONST 1 (1)
16 BINARY_ADD
17 SLICE+1
18 BINARY_ADD
19 STORE_GLOBAL 0 (a)
22 LOAD_CONST 0 (None)
25 RETURN_VALUE
None

Примечание: Во всех трех дизассемблированиях игнорируются последние две строки, которые в основном являются return None. Также первые две строки загружают глобальные значения a и index.

Ответ 4

Если вы хотите удалить элементы на определенных позициях в списке, например, 2-й, 3-й и 7-й элементы, вы не можете использовать

del my_list[2]
del my_list[3]
del my_list[7]

Поскольку после удаления второго элемента, третий элемент, который вы удаляете, фактически является четвертым элементом в исходном списке. Вы можете отфильтровать 2-й, 3-й и 7-й элементы в исходном списке и получить новый список, как показано ниже:

new_list = [j for i, j in enumerate(my_list) if i not in [2, 3, 7]]
2023-04-23 12:11 python list