Объявление членов только в конструкторе - PullRequest
7 голосов
/ 24 июля 2010

Я перехожу с C ++ на Python

Я объявил переменные-члены и установил их в C ++, например, так:

class MyClass:
    my_member = []

    def __init__(self,arg_my_member):
        self.my_member = arg_my_member

Затем я заметил в некотором открытом исходном коде, что первоначальное объявление my_member = [] было полностью исключено и создано только в конструкторе.

Что, очевидно, возможно, так как python является динамическим.

Мой вопрос таков: это предпочтительный или питонский способ ведения дел, и есть ли у него плюсы и минусы?

Ответы [ 4 ]

9 голосов
/ 24 июля 2010

То, как вы это делаете, означает, что теперь у вас будет «статический» член и «нестатический» член с тем же именем.

class MyClass:
    my_member = []

    def __init__(self, arg_my_member):
        self.my_member = arg_my_member


>>> a = MyClass(42)
>>> print a.my_member
42
>>> print MyClass.my_member
[]
4 голосов
/ 24 июля 2010

Если вы определяете его внутри класса, то это переменная класса, а если вы определяете его внутри конструктора, то это переменная объекта. Поэтому, если вы не определите его внутри конструктора, ВСЕ экземпляры класса совместно используют одну и ту же переменную класса.

1 голос
/ 24 июля 2010

Оба способа приемлемы для python, за исключением случая изменяемых значений.Когда вы объявляете это, как в вашем примере, вы можете получить очень неожиданный результат:

>>> class MyClass:
...     my_member = []
... 
>>> A = MyClass()
>>> B = MyClass()
>>> A.my_member.append(1)
>>> A.my_member
[1]
>>> B.my_member.append(2)
>>> B.my_member
[1, 2]
>>> A.my_member
[1, 2]
>>> MyClass.my_member
[1, 2]

Поскольку члены класса генерируются только один раз, когда сам класс обрабатывается при загрузке модуля.Если ваш член предназначен для использования в области видимости, вы должны установить его в __init__

Неизменные значения в порядке.

0 голосов
/ 24 июля 2010

Это создает атрибут класса с именем my_member

class MyClass:
    my_member = []

Если у экземпляров не было переменной экземпляра с именем my_member, все экземпляры имели бы доступ к тому же списку через self.my_member.

Поскольку вы создаете переменную экземпляра с именем my_member, вполне вероятно, что переменная класса никогда не используется и является просто признаком путаницы

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...