DEV Community

Discussion on: Dead Simple Python: Data Typing and Immutability

Collapse
 
codemouse92 profile image
Jason C. McDonald • Edited

Nope, it works exactly as it should. (And yes, iPython is an interactive shell "wrapper" to Python. No worries there.)

In CPython, the default implementation of Python, the integers 0-256 are interned in memory, meaning they are pre-defined for reasons of efficiency; there is never more than one 5 value in memory at any one time. (This is a bit like a singleton, though not quite.)

That's why this works...

a = 5
b = 5
print(a is b)  # prints True

There is only ever one value 5 in memory, which both a and b point to. Thus, they share an identity (both point to the same value in memory), and a is b returns True.

You can further see this if you run...

a = 5
b = 5
print(id(a))  # prints the memory location of 'a'
print(id(b))  # prints the memory location of 'b'

You'll see that both have the same id.

However, any integer above 256, while immutable, are not pre-defined. A new immutable value is created in memory each time you bind a name to the literal.

a = 500
b = 500
print(a is b)  # prints False

There are now two different 500 values in memory. a is bound to one of those, and b is bound to the other. Since they are not bound to the same location in memory (even though both locations contain the same data), they don't share an identity, and a is b is False.

Checking the id of each again...

a = 500
b = 500
print(id(a))  # prints the memory location of 'a'
print(id(b))  # prints the memory location of 'b'

You'll see that the two ids are different.

The immutable values None, True, False, the integers 0-256, and some strings are interned in memory! All other values, immutable or otherwise, are defined in memory when needed, so there may be multiple instances.

That's true of CPython, anyway; other implementations may behave differently. In fact, you should only ever count on None, True, and False being interned, which is why these are the only three values we typically use is with. For everything else, use ==, so identity doesn't matter.

I hope that helps!