Bug in __init__?
Bart Ogryczak
B.Ogryczak at addr.in.reply-to.invalid
Sun Jan 20 10:34:11 EST 2008
On 2008-01-18, citizen Zbigniew Braniecki testified:
> I found a bug in my code today, and spent an hour trying to locate it
> and then minimize the testcase.
>
> Once I did it, I'm still confused about the behavior and I could not
> find any reference to this behavior in docs.
>
> testcase:
>
> class A():
>
> def add (self, el):
> self.lst.extend(el)
>
> def __init__ (self, val=[]):
> print val
> self.lst = val
What you want probably is:
def __init__ (self, val=None):
if(val == None):
self.lst = []
else:
from copy import copy
### see also deepcopy
self.lst = copy(val)
> def test ():
> x = A()
> x.add(["foo1","foo2"])
> b = A()
>
>
> So, what I would expect here is that I will create two instances of
> class A with empty self.lst property. Right?
Wrong. default value for val gets evaluated only once, creating a list
(initialy empty). The same list for all of A's instances.
>>> a = A()
>>> id(a.lst)
13188912
>>> b = A()
>>> id(b.lst)
13188912
Moreover, self.lst = val, does not copy val, rather it creates binding
between self.list and val. So whatever you do to self.list, it affects
val (and vice-versa).
>>> x = []
>>> c = A(x)
>>> id(x)
10508368
>>> id(c.lst)
10508368
>>> c.lst.append('wrong')
>>> x
['wrong']
bart
--
"We're coming in low out of raising sun and about mile up we'll put on music"
http://candajon.azorragarse.info/ http://azorragarse.candajon.info/
More information about the Python-list
mailing list