What happens when you assign the value of one variable to another variable in Python?

As a C++ developer you can think of Python variables as pointers.

Thus when you write spam = 100, this means that you "assign the pointer", which was previously pointing to the object 42, to point to the object 100.

Earlier on, cheese was assigned to point to the same object as spam pointed to, which happened to be 42 at that time. Since you have not modified cheese, it still points to 42.

Immutability has nothing to do with it in this case, since pointer assignment does not change anything about the object being pointed to.


The way I see it there are different views of a language.

  • The "language lawyer" perspective.
  • The "practical programmer" perspective.
  • the "implementor" perspective.

From the language lawyer perspective python variables always "point at" an object. However unlike Java and C++ the behvaiour of == <= >= etc depends on the runtime type of the objects that the variables point at. Furthermore in python memory management is handled by the language.

From a practical programmer perspective we can treat the fact that integers, strings, tuples etc are immutable* objects rather than straight values as an irrelevent detail. The exception is when storing large ammounts of numeric data we may want to use types that can store the values directly (e.g. numpy arrays) rather than types that will end up with an array full of references to tiny objects.

From an implementers perspective most languages have some sort of as-if rule such that if the specified behaviours are correct the implementation is correct regardless of how things are actually done under the hood.

So yes your explanation is correct from a language lawyer perspective. Your book is correct from a practical programmer perspective. What an implementation actually does depends on the implementation. In cpython integers are real objects though small value integers are taken from a cache pool rather than created anew. I'm not sure what the other implementations (e.g. pypy and jython) do.

* note the distinction between mutable and immutable objects here. With a mutable object we have to be careful about treating it "like a value" because some other code might mutate it. With an immutable object we have no such concerns.


It is correct you can more or less thing of variables as pointers. However example code would help greatly with explaining how this actually is working.

First, we will heavily utilize the id function:

Return the “identity” of an object. This is an integer which is guaranteed to be unique and constant for this object during its lifetime. Two objects with non-overlapping lifetimes may have the same id() value.

It's likely this will return different absolute values on your machine.

Consider this example:

>>> foo = 'a string'
>>> id(foo) 
4565302640
>>> bar = 'a different string'
>>> id(bar)
4565321816
>>> bar = foo
>>> id(bar) == id(foo)
True
>>> id(bar)
4565302640

You can see that:

  • The original foo/bar have different ids, because they point to different objects
  • When bar is assigned to foo, their ids are now the same. This is similar to them both pointing to the same location in memory that you see in making a C++ pointer

when we change the value of foo, it is assigned to a different id:

>>> foo = 42
>>> id(foo)
4561661488
>>> foo = 'oh no'
>>> id(foo)
4565257832

An interesting observation too is that integers implicitly have this functionality up to 256:

>>> a = 100
>>> b = 100
>>> c = 100
>>> id(a) == id(b) == id(c)
True

However beyond 256 this is no longer true:

>>> a = 256
>>> b = 256
>>> id(a) == id(b)
True
>>> a = 257
>>> b = 257
>>> id(a) == id(b)
False

however assigning a to b will indeed keep the id the same as shown before:

>>> a = b
>>> id(a) == id(b)
True