trying to understand why a tuple is preferred over a list for a specific python example (from a tutorial)
I'm trying to learn what iterators and generators are in python, going through a tutorial i found online which used this fibonacci iterator as an example. I'm having trouble with the comment on lines 9-11. What does it mean that "the old values of self.fn1 and self.nf2 are used in assigning the new value"? I understand that tuples are immutable objects but i'm failing to see here why using tuple is preferred over a list. I guess I'm failing to see why using a tuple here is better than using a list and I would like to understand better if anyone can help explain it :/
4 class fibnum:
5 def __init__(self):
6 self.fn2 = 1 # "f_{n-2}"
7 self.fn1 = 1 # "f_{n-1}"
8 def next(self): # next() is the heart of a开发者_如何学Gony iterator
9 # note the use of the following tuple to not only save lines of
10 # code but also to insure that only the old values of self.fn1 and
11 # self.fn2 are used in assigning the new values
12 (self.fn1,self.fn2,oldfn2) = (self.fn1+self.fn2,self.fn1,self.fn2)
13 return oldfn2
14 def __iter__(self):
15 return self
from : http://heather.cs.ucdavis.edu/~matloff/Python/PyIterGen.pdf
These is no difference in functionality here between using a tuple
versus a list
. The point they are trying to make is that it's good to do it in one statement.
If you were to split that single line into multiple statements, you'd end up with something like:
oldfn2 = self.fn2
self.fn2 = self.fn1
self.fn1 = self.fn1 + oldfn2
return oldfn2
There's no point in using a list
here, because you're always dealing with three elements, rather than a variable number of them. By "insure [sic] that only the old values of self.fn1
and self.fn2
are used in assigning the new values", the programmer seems to be comparing this method with the alternative:
self.fn1 = X
self.fn2 = Y
oldfn2 = Z
which wouldn't work out of the box since self.fn1
is reassigned before its old value can be assigned to self.fn2
. Reordering the assignments can fix that, but with the tuple assignment, you don't need to worry about the order.
This could have been written without the parens, btw:
self.fn1, self.fn2, oldfn2 = self.fn1+self.fn2, self.fn1, self.fn2
The comment means that instead of using multiple assignments like this:
# would be incorrect
self.fn1 = self.fn1+self.fn2 # because fn1 is overwritten here
self.fn2 = self.fn1
oldfn2 = self.fn2
they use tuple assignment:
(self.fn1,self.fn2,oldfn2) = (self.fn1+self.fn2,self.fn1,self.fn2)
which is shorter and also ensured that all new values are calculated before the first assignment happens.
精彩评论