[Tutor] how to *really* copy a list
John Fouhy
john at fouhy.net
Fri Apr 28 04:14:07 CEST 2006
On 28/04/06, kevin parks <kp8 at mac.com> wrote:
> In most case you are fine operating on the list in place and altering the
> existing list. In some cases you want your code to stop molesting your poor
> mutables and really honestly sincerly copy the dang thing. In this case i am
> making a function that does odd smmetry mirroring. But i want my orginal list
> to remain intact....
>
> def mirror(seq):
> """odd symmetry mirroring [1, 2, 3, 4] --> [1, 2, 3, 4, 3, 2, 1]"""
> foo=seq[:-1] # copy list, excluding last element for odd symetry
> foo.reverse() # flip it
> seq.extend(foo)
> return seq
Hi Kevin,
Your problem is this line:
seq.extend(foo)
This is the line that mutates your original list.
There are a few ways you could procede here. One way is to make a
copy of the argument, like this:
def mirror(seq):
start = list(seq)
end = seq[:-1]
end.reverse()
start.extend(end)
return start
Notice that we've not calling any methods on seq, so seq won't be
changed. The first line, "start = list(seq)", instructs python to
build a new list out of the elements of seq. You could also write
"start = seq[:]" here --- I'm not sure which is the preferred way.
Another option is to use arithmetic --- you can add lists together,
and this creates a new list. eg:
def mirror(seq):
end = seq[:-1]
end.reverse()
return seq + end
Finally, just a side comment: You can use slicing to reverse the end
for you as well. So, we could rewrite the last function as:
def mirror(seq):
end = seq[-2::-1]
return seq + end
Which means there is a one-line version as well:
def mirror(seq):
return seq + seq[-2::-1]
HTH!
--
John.
More information about the Tutor
mailing list