Вопрос по python – переменная класса python не видна в __init__?

8

Этот код выдает сообщение об ошибке, которое я нахожу удивительным:

class Foo(object):
    custom = 1
    def __init__(self, custom=Foo.custom):
        self._custom = custom

x = Foo()

Может ли кто-нибудь обеспечить просветление?

Ваш Ответ

4   ответа
6

class Foo( object ):
    custom = 1
    def __init__( self, arg=None )
        self._custom = self.custom if arg is None else arg

Это обходит запутанный вопрос о том, является ли имяFoo был определен еще.

Error: User Rate Limit ExceededinitError: User Rate Limit Exceeded
Error: User Rate Limit Exceeded
2

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

Это потому что имяFoo находится в процессе определения как__init__ Функция определена и не полностью доступна в то время.

Решение состоит в том, чтобы избежать использования имениFoo в определении функции (я также переименовалcustom параметр дляacustom отличить его отFoo.custom):

class Foo(object):
    custom = 1
    def __init__(self, acustom=custom):
        self._custom = acustom
x = Foo()
print x._custom
Error: User Rate Limit ExceededbodyError: User Rate Limit ExceededinitError: User Rate Limit Exceeded
Error: User Rate Limit Exceeded
11

Foo это не видно, потому что вы находитесь в процессе его создания. Но поскольку вы находитесь в том же объеме, что иcustomможно просто сказатьcustom скорее, чемFoo.custom:

class Foo(object):
    custom = 1
    def __init__(self, mycustom=custom):
        self._custom = mycustom

Но обратите внимание, что изменениеFoo.custom позже не повлияет на стоимостьcustom впоследствии созданныйFooсмотри:

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

Используя вместо этого значение по умолчанию, вы можете получить то, что хотите:

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
Error: User Rate Limit ExceededrunError: User Rate Limit ExceededinitError: User Rate Limit ExceededinitError: User Rate Limit Exceededdefining initError: User Rate Limit Exceeded
Error: User Rate Limit ExceededifError: User Rate Limit Exceeded
Error: User Rate Limit Exceededis.
Error: User Rate Limit ExceededinitError: User Rate Limit Exceeded
Error: User Rate Limit ExceededinitError: User Rate Limit Exceeded
3

как будет определен сам класс, поэтому значения аргументов по умолчанию не могут ссылаться на класс. Просто делаяcustom по умолчанию (без квалификации класса) должно работать.

Похожие вопросы