reference or pointer to some object?
jeff at ccvcorp.com
Thu Jan 13 16:03:09 EST 2005
Torsten Mohr wrote:
> But i think my understanding was wrong (though it is not yet
> clear). If i hand over a large string to a function and the
> function had the possibility to change it, wouldn't that mean
> that it is necessary to hand over a _copy_ of the string?
> Else, how could it be immutable?
Anything which might change the string, can only do so by returning a
>>> a = "My first string"
>>> b = a.replace('first', 'second')
'My second string'
'My first string'
Saying that strings are immutable means that, when 'a' is pointing to
a string, the (string) object that 'a' points to will always be the
same. (Unless 'a' is re-bound, or someone uses some deep black magic
to change things "behind the scenes"...) No method that I call on
'a', or function that I pass 'a' to, can alter that object -- it can
only create a new object based off of the original. (You can
demonstrate this by checking the id() of the objects.)
Mutable objects, on the other hand, can change in place. In the case
of lists, for example, it will stay the same list object, but the list
contents can change.
Note, also, that passing a string into a function does not copy the
string; it creates a new name binding (i.e. reference) to the same object.
>>> def func(item):
... print "Initial ID:", id(item)
... item = item.replace('first', 'second')
... print "Resulting ID:", id(item)
Initial ID: 26278416
Resulting ID: 26322672
> Thinking about all this i came to the idea "How would i write
> a function that changes a string with not much overhead?".
Since strings cannot really be changed, you simply try to minimize the
number of new strings created. For example, appending to a string
inside of a for-loop creates a new string object each time, so it's
generally more efficient to convert the string to a list, append to
the list (which doesn't create a new object), and then join the list
together into a string.
> def func(s):
> change s in some way, remove all newlines, replace some
> charaters by others, ...
> return s
> s = func(s)
> This seems to be a way to go, but it becomes messy if i hand over
> lots of parameters and expect some more return functions.
This has the advantage of being explicit about s being (potentially)
changed. References, in the way that you mean them, are even messier
in the case of numerous parameters because *any* of those parameters
might change. By simply returning (new) objects for all changes, the
function makes it very clear what's affected and what isn't.
More information about the Python-list