In Python, objects are never explicitly destroyed. However, they may be garbage-collected when they become unreachable.
The del
statement deletes names, not objects. An object may be garbage collected as result of a del
command, but only if the variable deleted holds the last reference to the object, or if the object becomes unreachable.
In CPython, the primary algorithm for garbage collection is reference counting. Essentially each object keeps count fo how many references point to it. As soon as that refcount
reaches 0, the object is immediately destroyed: CPython calls the __del__
method on the object (if defined) and the frees the memory.
But sometimes, it is useful to have a reference to an object that does not keep it around longer than necessary. Week references to an object do not increase its reference count. A weak reference does not prevent the referent from being garbage collected.
The following example shows how a weakref.ref
instance can be called to reach its referent.
import weakref
s = {0,1}
wref = weakref.ref(s)
print(wref) # <weakref at 0x10767bb88; to 'set' at 0x1076a5f28>
print(wref()) # {0, 1}
s = {2,3,4}
print(wref) # <weakref at 0x109871b88; dead>
print(wref()) # None
print(wref() is None) # True
WeekValueDictionary
The class WeekValueDictionary
implements a mutable mapping where the values are weak reference to objects. When a referred object is garbage collected, the corresponding key is automatically removed from the WeekValueDictionary
. This is commonly used for caching.
class Cheese:
def __init__(self, kind):
self.kind = kind
def __repr__(self):
return 'Cheese(%r)' % self.kind
import weakref
stock = weakref.WeakValueDictionary()
catalog = [Cheese('Red Leicester'), Cheese('Tilsit'),
Cheese('Brie'), Cheese('Parmesan')]
for ce in catalog:
stock[ce.kind] = ce
print(sorted(stock.keys())) # ['Brie', 'Parmesan', 'Red Leicester', 'Tilsit']
del catalog
print(sorted(stock.keys())) # ['Parmesan']
del ce
print(sorted(stock.keys())) # []
After catelog
is deleted, most cheeses are gone from the stock
except one. Because a temporary variable may cause an object to last longer than expected by holding a reference to it.
A counterpart to the WeakValueDictionary
is WeakKeyDictionary
in which the keys are week references. WeakKeyDictionary
can be used to associate additional data with an object owned by other parts of an application without adding attributes to those objects.
Limitations of week references
Not every Python object may be the target of a weak reference. Basic int
, tuple
, list
and dict
instances may not be referents.
Reference