Python mutable and immutable… everything is an object!

Edy Yazmin Giraldo
4 min readOct 7, 2021

--

Photo by Michael Dziedzic on Unsplash

When you start to learn Python, the first thing you need to know is that in Python everything is an object: a string, a number, a list, a dictionary, a tuple, etc. But what does it mean? Objects combine data values with behavior, which means that every object has some metadata and associated functionality.

We call attributes to the metadata of the object and methods to the functionality of every object. They can be created by the instantiation of a class.

Now let’s talk about some functions that can reveal interesting information about objects:

Type

This is a built-in function that returns the class type of the object passed as parameter.

The syntax for this function is:

type(object)

Let’s see an example:

> type(8)
<class 'int'>
> type("Hello world")
<class 'str'>
> type(True)
<class 'bool'>

Identifier

The id() function returns the identity of the object, which is a unique number that the system assign. The syntax for this function is:

id(object)

Let’s see an example:

> number = 8
> string = "Hello world"
> id(number)
9789216
> id(string)
9484384

Mutable and immutable objects

As we discussed before, in Python everything is an object and each of them can be categorized as mutable and immutable.

What is a mutable object?

This type of object can be modified after its creation. Here, we can find lists, dictionaries, sets and even user-defined classes. An example:

> list = [1, 2, 3]
> list[0] = 9
> print(list)
[9, 2, 3]

First, we define a list with three integers in it. Then, we change the first value of the list with its index 0 and print the list. As we see, the first value of the list has been changed correctly.

What is an immutable object?

This type of object can’t be modified after its creation. These are integers, floats, strings, tuples and frozen sets. Let’s see an example:

Example with a string:

> string = "Betty Holberton"
> string[0] = "b"
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: 'str' object does not support item assignment

Example with a tuple:

> tuple = (1, 2, 3)
> tuple[0] = 0
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: 'tuple' object does not support item assignment

In this case, we need to pay special attention to this object. Although a tuple is an immutable object, it has a surprising trait. Why? Well, you can assign a mutable value to a tuple… like a list:

> tuple = (1, ["List", "inside", "tuple"])
> list = tuple[1]
> list.append("Awesome!")
> print(tuple
(1, ["List", "inside", "tuple", "Awesome!"])

Great, right? I recommend you this article to understand the special behavior of tuples.

How are objects stored in memory?

To understand better how mutable and immutable objects works, we need to go deeper: to the memory allocation.

Let’s assign two variables to the same string:

> a = "Betty"
> b = "Betty"

We can see that they have the same content if we type in a terminal:

> a == b
True

The comparison operator == checks for the equality of content. It’s clear that both objects point to the same content. Now, we can test whether two names refer to the same object using the is operator.

> a is b
True

How can be this possible? Two different variables with two different names referring to the same object? That’s correct. Python will make two variables that point to the same string refer to the same object to optimize resources.

We can check this correspondence with the id() function:

> id(a)
9582314
> id(b)
9582314

They are the same object!

https://bit.ly/3Dm9Z9Z

Nevertheless, this is not the case with mutable objects like lists:

> list_1 = [1, 2, 3]
> list_2 = [1, 2, 3]
> list_1 == list_2
True
> list_1 is list_2
False

We declare two lists with the same value, but regardless of their equality of content, they do not refer to the same object.

Aliasing

There is a scenario where two mutable objects will refer to the same object: it’s time to introduce you to the concept of aliasing.

We know that variables refer to objects, so if we assign a variable to another one, both will refer to the same object:

> list = [1, 2, 3]
> other_list = list
> other_list is list
True

Here the same list has two different variables pointing to it, but if you change one alias, the other one will be affected.

> other_list[1] = "Boo!"
> print(list)
[1, "Boo!", 3]
> print(other_list)
[1, "Boo!", 3]

How does it work with immutable objects?

Well, this changing-values behavior will not affect the immutable objects because… they are immutable.

string = "Hello world"
other_string = string

As we saw before, at this point they are referencing to the same object and they have the same content. Now is when Python sees an opportunity to economize, but it all changes if we modify the value of one of the objects.

> string = "I changed"
> print(string)
I changed
> print(other_string)
Hello world

I hope this article helped you to understand objects in Python!

--

--

Edy Yazmin Giraldo
Edy Yazmin Giraldo

No responses yet