[Tutor] What does Python gain by having immutable types?
Danny Yoo
dyoo at hkn.eecs.berkeley.edu
Tue Nov 15 03:38:55 CET 2005
> > Quite often the only answer is "just because". Some features are the
> > way they are because that's Guido's pesonal preference. Others may
> > disagree with him but it's his language and he gets to pick what he
> > thinks is best - the benign dictator syndrome.
Hi Hugo,
There are a few languages that have immutable values. For example, C and
Java both define string literals to be immutable: trying to mutate them
causes an error. (Well, C is supposed to raise a segmentation fault.)
There are strong advantages to immutability: one of the main ones is that
side-effect-less programming is less prone to certain kinds of bugs.
For example, let's say we wanted a function to squish values together:
######
>>> def squish(A, B):
... """Creates a new list containing the elements of A and B"""
... result = []
... result.extend(A)
... result.extend(B)
... return result
...
>>> squish(range(5), range(7, 9))
[0, 1, 2, 3, 4, 7, 8]
######
An alternative way to write this might be:
######
>>> def smash(A, B):
... """Creates a new list containing the elements of A and B.
... Smashes the existing list A."""
... A.extend(B)
... return A
...
>>> smash(range(5), range(7, 9))
[0, 1, 2, 3, 4, 7, 8]
######
These both appear to have the same behavior but of course we know that
something must be different between the two. *grin*
If we have two lists, like:
######
>>> firstNames = ['hugo', 'keanu']
>>> lastNames = ['weaving', 'reeves']
######
we can squish() them together:
######
>>> squish(firstNames, lastNames)
['hugo', 'keanu', 'weaving', 'reeves']
>>>
>>> firstNames
['hugo', 'keanu']
>>> lastNames
['weaving', 'reeves']
######
... or we can smash() them:
######
>>> smash(firstNames, lastNames)
['hugo', 'keanu', 'weaving', 'reeves']
>>>
>>> firstNames
['hugo', 'keanu', 'weaving', 'reeves']
>>> lastNames
['weaving', 'reeves']
######
Oh!
Notice that smash() messes with the list named by firstNames; when we
finish calling it, we see a side effect: firstNames is smashed. The issue
here is that we've let ourselves mutate our input values. Of course this
is an exaggerated example, but it tries to make a point: having mutable
values means we have to think about mutation. Mutation introduces a kind
of "leakage" between functions.
To make the situation more extreme: if we are working with someone else's
code, and if we pass a mutable value to that external code, then if we see
a bug later on in our own program, we may have to wonder if the external
code mutated our values. That can be a big pain.
(C programmers have to worry about this ALL THE TIME because they have
pointers that let anyone smash up everything. *grin*)
If we guarantee, though, that we are working with immutable values, we can
toss them with abandon at anyone and know that they won't get munged.
That's why immutability is an important concept in a programming language,
and an especially useful one in a collaborative language like Python.
Does this make sense? If you have more questions, please feel free to
ask.
More information about the Tutor
mailing list