I want to understand why:
a = []
;del a
; anddel a[:]
;behave so differently.
I ran a test for each to illustrate the differences I witnessed:
>>> # Test 1: Reset with a = []
...
>>> a = [1,2,3]
>>> b = a
>>> a = []
>>> a
[]
>>> b
[1, 2, 3]
>>>
>>> # Test 2: Reset with del a
...
>>> a = [1,2,3]
>>> b = a
>>> del a
>>> a
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
NameError: name 'a' is not defined
>>> b
[1, 2, 3]
>>>
>>> # Test 3: Reset with del a[:]
...
>>> a = [1,2,3]
>>> b = a
>>> del a[:]
>>> a
[]
>>> b
[]
I did find Different ways of clearing lists, but I didn't find an explanation for the differences in behaviour. Can anyone clarify this?
There are three ways in which you can Remove elements from List: Using the remove() method. Using the list object's pop() method. Using the del operator.
There are two remove() methods to remove elements from the List. E remove(int index): This method removes the element at the specified index and return it. The subsequent elements are shifted to the left by one place. This method throws IndexOutOfBoundsException is the specified index is out of range.
>>> a = [1,2,3] # set a to point to a list [1, 2, 3]
>>> b = a # set b to what a is currently pointing at
>>> a = [] # now you set a to point to an empty list
# Step 1: A --> [1 2 3]
# Step 2: A --> [1 2 3] <-- B
# Step 3: A --> [ ] [1 2 3] <-- B
# at this point a points to a new empty list
# whereas b points to the original list of a
>>> a = [1,2,3] # set a to point to a list [1, 2, 3]
>>> b = a # set b to what a is currently pointing at
>>> del a # delete the reference from a to the list
# Step 1: A --> [1 2 3]
# Step 2: A --> [1 2 3] <-- B
# Step 3: [1 2 3] <-- B
# so a no longer exists because the reference
# was destroyed but b is not affected because
# b still points to the original list
>>> a = [1,2,3] # set a to point to a list [1, 2, 3]
>>> b = a # set b to what a is currently pointing at
>>> del a[:] # delete the contents of the original
# Step 1: A --> [1 2 3]
# Step 2: A --> [1 2 3] <-- B
# Step 2: A --> [ ] <-- B
# both a and b are empty because they were pointing
# to the same list whose elements were just removed
Of your three "ways of deleting Python lists", only one actually alters the original list object; the other two only affect the name.
a = []
creates a new list object, and assigns it to the name a
.del a
deletes the name, not the object it refers to.del a[:]
deletes all references from the list referenced by the name a
(although, similarly, it doesn't directly affect the objects that were referenced from the list).It's probably worth reading this article on Python names and values to better understand what's going on here.
Test 1:
rebinds a
to a new object, b
still holds a reference to the original object, a
is just a name by rebinding a
to a new object does not change the original object that b
points to.
Test 2:
you del the name a
so it no longer exists but again you still have a reference to the object in memory with b
.
Test 3
a[:]
just like when you copy a list or want to change all the elements of a list refers to references to the objects stored in the list not the name a
. b
gets cleared also as again it is a reference to a
so changes to the content of a
will effect b
.
The behaviour is documented:
There is a way to remove an item from a list given its index instead of its value: the
del
statement. This differs from thepop()
method which returns a value. Thedel
statement can also be used to remove slices from a list or clear the entire list (which we did earlier by assignment of an empty list to the slice). For example:>>> >>> a = [-1, 1, 66.25, 333, 333, 1234.5] >>> del a[0] >>> a [1, 66.25, 333, 333, 1234.5] >>> del a[2:4] >>> a [1, 66.25, 1234.5] >>> del a[:] >>> a []
del
can also be used to delete entire variables:>>> >>> del a
Referencing the name
a
hereafter is an error (at least until another value is assigned to it). We'll find other uses fordel
later.
So only del a
actually deletes a
, a = []
rebinds a to a new object and del a[:]
clears a
. In your second test if b
did not hold a reference to the object it would be garbage collected.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With