[Tutor] Python oddity

Brett Wilkins lupin at orcon.net.nz
Thu Feb 28 13:26:31 CET 2008


Cheers, I actually forgot about the whole shallow-copy thing, and 
deepcopy(). I'm only new to the language myself, I just remembered about 
the slice copy and thought to mention it.

Luke Paireepinart wrote:
> Brett Wilkins wrote:
>> As everybody else has told you, assigning bb = aa just gives bb the 
>> reference to the same object that aa has. Unless I missed something, 
>> then nobody's actually mentioned how to make this not happen... and 
>> it's actually rather easy... instead of bb = aa, do this:
>> bb = aa[:]
>> Looks like a splice, and indeed it is a splice, without bounds. When 
>> a splice is used like this, I believe it is known as the copy directive.
> Yes, Terry explained other ways as well.
> The problem with using slices is the following:
>
> >>> a = [['a'],'b']
> >>> b = a
> >>> b is a
> True
> >>> b = a[:]
> >>> b is a
> False
> #okay, we're fine so far.
> >>> b[0]
> ['a']
> >>> b[0].append('c')
> >>> b[0]
> ['a', 'c']
> >>> a[0]
> ['a', 'c']
>
>
> and here's where we run into problems.
> Turns out the slice notation just makes a shallow copy, so if you have 
> any lists in your list, they will still refer to the same object.  
> (I'm guessing that any mutable objects will still refer to the same 
> object)
> copy.copy() has this same problem.
> The way to avoid this, as I mentioned before, is to use a deepcopy(), 
> but as I said, you usually don't need to make a full copy of a list.
> Oh, and if you're curious:
> >>> b = list(a)
> >>> b is a
> False
> >>> b[0].append('d')
> >>> a[0]
> ['a', 'c', 'd']
>
> So a list() does a shallow copy as well.
>
> Here's a continuation, with deepcopy():
> >>> import copy
> >>> b = copy.deepcopy(a)
> >>> b is a
> False
> >>> b[0] is a[0]
> False
> >>> b[0].append('e')
> >>> a[0]
> ['a', 'c', 'd']
>
>
> HTH,
> -Luke
>


More information about the Tutor mailing list