This code produces an error message, which I found surprising:
class Foo(object):
custom = 1
def __init__(self, custom=Foo.custom):
self._custom
I get the following error:
Traceback (most recent call last):
Line 1, in <module>
class Foo(object):
Line 3, in Foo
def __init__(self, custom=Foo.custom):
NameError: name 'Foo' is not defined
This is because the name Foo
is in the process of being defined as the __init__
function is defined, and is not fully available at that time.
The solution is to avoid using the name Foo
in the function definition (I also renamed the custom
paramter to acustom
to distinguish it from Foo.custom
):
class Foo(object):
custom = 1
def __init__(self, acustom=custom):
self._custom = acustom
x = Foo()
print x._custom
It's Foo
that isn't visible, because you're in the middle of building it. But since you're in the same scope as custom
, you can just say custom
rather than Foo.custom
:
class Foo(object):
custom = 1
def __init__(self, mycustom=custom):
self._custom = mycustom
But note that changing Foo.custom
later on won't affect the value of custom
that subsequently-created Foo
s see:
class Foo(object):
custom = 1
def __init__(self, mycustom=custom):
self._custom = mycustom
one = Foo()
Foo.custom = 2
two = Foo()
print (two._custom) # Prints 1
By using a sentinel default value instead, you can get what you want:
class Foo(object):
custom = 1
def __init__(self, mycustom=None):
if mycustom is None:
self._custom = Foo.custom
else:
self._custom = mycustom
one = Foo()
Foo.custom = 2
two = Foo()
print (two._custom) # Prints 2
What we do instead is the following
class Foo( object ):
custom = 1
def __init__( self, arg=None )
self._custom = self.custom if arg is None else arg
This bypasses the confusing issue of whether or not the name Foo
has been defined yet.
The class body is executed before the class its self is defined, so default argument values can't reference the class. Just making custom
the default (without class qualification) should work.