Weak References in Python
Last Updated :
27 Apr, 2022
Python’s memory management algorithm uses a reference counting mechanism for garbage collection, which tracks all reachable objects. All Python objects include a reference count field, which counts how many objects are referencing it. If an object is referenced by another object, then its counter is set to a non-zero number and the object can’t be garbage collected. If the counter reaches zero, the garbage collector will free that object.
Below is a short example of how can we find the reference count of any object in python.
Python3
import ctypes
my_list = [ 1 , 2 , 3 ]
my_list_address = id (my_list)
ref_count = ctypes.c_long.from_address(my_list_address).value
print (f "Reference count for my_list is: {ref_count}" )
|
Output:
Reference count for my_list is: 1
So, now as we are clear with the basics of references and garbage collections let’s move to what are weak references and why do we need them?
What is Weak Reference?
Unlike the references we discussed above, a weak reference is a reference that does not protect the object from getting garbage collected. Why do we want such a thing in the first place?
There are two main applications of weak references:
- Implement caches for large objects (weak dictionaries).
- Reduction of Pain from circular references.
To create weak references, Python has provided us with a module named weakref. A point to keep in mind before using weakref is that some builtins such as tuple or int do not support this. list and dict support is either but we can add support through subclassing. Let’s discuss the applications in detail.
Weakref module
Sometimes a large object is stored in the cache so there is no need to keep it alive. Let’s you have a large number of image objects and they are being used as keys to map to images due to which these objects will be kept alive.
Fortunately, weakref module provides something called as WeakKeyDictionary and WeakValueDictionary doesn’t keep the objects alive as they appear in the mapping objects.
The following classes and methods are provided by weakref module:
- class weakref.ref(object[, callback]) – This returns a weak reference to the object.
- weakref.proxy(object[, callback]) – This returns a proxy to object which uses a weak reference.
- weakref.getweakrefcount(object) – Return the number of weak references and proxies which refer to object.
- weakref.getweakrefs(object) – Return a list of all weak reference and proxy objects which refer to object.
Let’s understand the work with some examples:
Example 1:
In the below-given example, we create a normal list object, a weak reference list object, and a proxy list object and print the weak reference count for all of them.
Python3
import weakref
class GFG( list ):
pass
obj = GFG( "Geeks" )
normal_list = obj
print (f "This is a normal object: {normal_list}" )
weak_list = weakref.ref(obj)
weak_list_obj = weak_list()
print (f "This is a object created using weak reference: {weak_list_obj}" )
proxy_list = weakref.proxy(obj)
print (f "This is a proxy object: {proxy_list}" )
for objects in [normal_list, weak_list_obj, proxy_list]:
print (f "Number of weak references: {weakref.getweakrefcount(objects)}" )
|
Output:
This is a normal object: [‘G’, ‘e’, ‘e’, ‘k’, ‘s’]
This is a object created using weak reference: [‘G’, ‘e’, ‘e’, ‘k’, ‘s’]
This is a proxy object: [‘G’, ‘e’, ‘e’, ‘k’, ‘s’]
Number of weak references: 2
Number of weak references: 2
Number of weak references: 0
As the normal object has references to the weak reference object hence both of them have a weak reference count of 2 but as proxy_object is a proxy created from the weak reference thus it does not have a reference count.
Example 2:
In this example, we will see how to use WeakValueDictionary which we discussed earlier in the article.
Python3
import weakref
class GFG:
def __init__( self ,data):
self .data = data
def __repr__( self ):
return str ( self .data)
value = GFG( 5 )
weak_dict = weakref.WeakValueDictionary()
weak_dict[ "num" ] = value
print (f 'Weak reference count is: {weakref.getweakrefcount(weak_dict)}' )
del weak_dict
|
Output:
Weak reference count is: 1
In the above example, we assumed that there is a really large object which has been placed in the cache so we have created a weak ref dictionary to store that key and value pair so it will be garbage collected.
Similar Reads
range() vs xrange() in Python
The range() and xrange() are two functions that could be used to iterate a certain number of times in for loops in Python. In Python3, there is no xrange, but the range function behaves like xrange in Python2. If you want to write code that will run on both Python2 and Python3, you should use range(
4 min read
Working with Unicode in Python
Unicode serves as the global standard for character encoding, ensuring uniform text representation across diverse computing environments. Python, a widely used programming language, adopts the Unicode Standard for its strings, facilitating internationalization in software development. This tutorial
3 min read
What's new in Python 3.9?
A new version of Python is coming! Soon, we'll be using it in our Python projects. As of 20/07/2020 Python 3.9 is in beta version(3.9.0b4) and will release the full version of Python 3.9 pretty soon. Enough of introduction. Let's get started and learn about the new features. 1. Dictionary merge and
3 min read
Python range() function
The Python range() function returns a sequence of numbers, in a given range. The most common use of it is to iterate sequences on a sequence of numbers using Python loops. Example In the given example, we are printing the number from 0 to 4. [GFGTABS] Python for i in range(5): print(i, end="
7 min read
set copy() in python
The copy() method returns a shallow copy of the set in python. If we use "=" to copy a set to another set, when we modify in the copied set, the changes are also reflected in the original set. So we have to create a shallow copy of the set such that when we modify something in the copied set, change
2 min read
Working with Strings in Python 3
In Python, sequences of characters are referred to as Strings. It used in Python to record text information, such as names. Python strings are "immutable" which means they cannot be changed after they are created. Creating a StringStrings can be created using single quotes, double quotes, or even tr
6 min read
Python Set - remove() method
Python remove() Function is a built-in method to remove elements from the set. remove() method takes exactly one argument. Syntax set.remove(element) If the element passed to the remove() is present in the set then the element will be removed from the set. If the element passed to the remove() is no
1 min read
Python - Multi-Line Statements
In this article, we are going to understand the concept of Multi-Line statements in the Python programming language. Statements in Python: In Python, a statement is a logical command that a Python interpreter can read and carry out. It might be an assignment statement or an expression in Python. Mul
3 min read
Python Random - random() Function
There are certain situations that involve games or simulations which work on a non-deterministic approach. In these types of situations, random numbers are extensively used in the following applications: Creating pseudo-random numbers on Lottery scratch cardsreCAPTCHA on login forms uses a random nu
3 min read
Python Version History
Python, one of the most popular programming languages today, has a rich history of development and evolution. From its inception in the late 1980s to its current status as a versatile and powerful language, Python's version history reflects the language's adaptability and the community's dedication
5 min read