Есть ли какая-либо причина для объявления класса наследовать object?
Я только что нашел код, который делает это, и я не могу найти вескую причину, почему.
class MyClass(object):
# class code follows...
Есть ли какая-либо причина для объявления класса наследовать object?
Я только что нашел код, который делает это, и я не могу найти вескую причину, почему.
class MyClass(object):
# class code follows...
Ответы:
Есть ли какая-либо причина для объявления класса наследовать
object?
В Python 3, кроме совместимости между Python 2 и 3, нет причин . В Python 2 много причин .
В Python 2.x (начиная с 2.2) есть два стиля классов в зависимости от наличия или отсутствия objectв качестве базового класса:
классические классы стиля : они не имеют objectбазового класса:
>>> class ClassicSpam: # no base class
... pass
>>> ClassicSpam.__bases__
()«новые» классы стилей : они имеют, прямо или косвенно (например, наследуют от встроенного типа ), objectв качестве базового класса:
>>> class NewSpam(object): # directly inherit from object
... pass
>>> NewSpam.__bases__
(<type 'object'>,)
>>> class IntSpam(int): # indirectly inherit from object...
... pass
>>> IntSpam.__bases__
(<type 'int'>,)
>>> IntSpam.__bases__[0].__bases__ # ... because int inherits from object
(<type 'object'>,)Без сомнения, при написании класса вы всегда захотите перейти на классы нового стиля. Льготы для этого многочисленны, чтобы перечислить некоторые из них:
Поддержка дескрипторов . В частности, следующие дескрипторы стали возможными с помощью дескрипторов:
classmethod: Метод, который получает класс в качестве неявного аргумента вместо экземпляра.staticmethod: Метод, который не получает неявный аргумент selfв качестве первого аргумента.property: Создание функций для управления получением, установкой и удалением атрибута.__slots__Сохраняет потребление памяти классом, а также ускоряет доступ к атрибутам. Конечно, это накладывает ограничения .__new__Статический метод: позволяет настроить как новые создаются экземпляры класса.
Порядок разрешения методов (MRO) : в каком порядке будут искать базовые классы класса при попытке определить, какой метод вызывать.
Связанные с MRO, superзвонки . Также смотрите, super()считается супер.
Если вы не наследуете object, забудьте об этом. Более полное описание предыдущих пунктов маркировки наряду с другими преимуществами «новых» классов стилей можно найти здесь .
Одним из недостатков классов нового стиля является то, что сам класс требует больше памяти. Если, конечно, вы не создаете много объектов класса, я сомневаюсь, что это будет проблемой, и это будет негативное погружение в море позитива.
В Python 3 все упрощено. Существуют только классы нового стиля (именуемые просто классами), поэтому единственное отличие в добавлении objectсостоит в том, что требуется ввести еще 8 символов. Эта:
class ClassicSpam:
pass
полностью эквивалентно (кроме их имени :-) этому:
class NewSpam(object):
pass
и к этому:
class Spam():
pass
Все имеют objectпо своему __bases__.
>>> [object in cls.__bases__ for cls in {Spam, NewSpam, ClassicSpam}]
[True, True, True]
В Python 2: всегда наследовать от objectявно . Получи льготы.
В Python 3: наследовать, objectесли вы пишете код, который пытается быть независимым от Python, то есть он должен работать как в Python 2, так и в Python 3. В противном случае это не имеет никакого значения, поскольку Python вставляет его для вас. за кулисами.
object. IIRC был момент, когда еще не все встроенные типы были перенесены в классы нового стиля.
object. У меня есть Python 2.2.3, и после быстрой проверки я не смог найти нарушителя, но позже я перефразирую ответ, чтобы сделать его более понятным. Было бы интересно, если бы вы могли найти пример, мое любопытство задето.
object.
staticmethodи classmethodотлично работает даже на уроках старого стиля. propertyСорта работает для чтения в классах старого стиля, просто не перехватывает записи (поэтому, если вы присваиваете имя, экземпляр получает атрибут с заданным именем, который скрывает свойство). Также обратите внимание, что __slots__улучшение скорости доступа к атрибутам в основном сводится к устранению потерь, связанных с доступом к атрибутам классов нового стиля, поэтому это не совсем выгодно для классов нового стиля (хотя экономия памяти - это точка продажи).
Python 3
class MyClass(object): = Новый стильclass MyClass:= Новый стиль класса (неявно наследуется от object)Python 2
class MyClass(object): = Новый стильclass MyClass:= СТАРЫЙ СТИЛЬ КЛАССПояснение :
При определении базовых классов в Python 3.x вы можете удалить objectиз определения. Тем не менее, это может открыть дверь для серьезного трудно отслеживаемой проблемы ...
Python представил классы нового стиля еще в Python 2.2, и к настоящему времени классы старого стиля действительно довольно старые. Обсуждение классов в старом стиле скрыто в документах 2.x и отсутствует в документах 3.x.
Проблема заключается в том , что синтаксис для классов старого стиля в Python 2.x является такой же , как альтернативный синтаксис для новых классов в Python 3.x . Python 2.x по-прежнему очень широко используется (например, GAE, Web2Py), и любой код (или кодер), невольно вносящий определения классов в стиле 3.x в код 2.x, в конечном итоге будет иметь некоторые серьезно устаревшие базовые объекты. А поскольку классы старого стиля ни на чём не находятся, они, вероятно, не будут знать, что их поразило.
Так что просто разберитесь в этом долгий путь и сэкономьте разработчику 2.x слезы.
__metaclass__ = typeв верхнюю часть модуля (после from __future__ import absolute_import, division, print_functionстроки :-)); это хак совместимости в Py2, который делает все впоследствии определенные классы в модуле новым стилем по умолчанию, а в Py3 он полностью игнорируется (просто случайная глобальная переменная сидит без дела), поэтому он безвреден.
Да, это объект «нового стиля». Это была функция, представленная в python2.2.
Новые объекты типа имеют различную объектную модель для классических объектов, и некоторые вещи не будут работать должным образом со старыми объектами типа, например, super(), @propertyи дескрипторы. См. Эту статью для хорошего описания того, что новый класс стиля.
Так что ссылка для описания различий: В чем разница между старым стилем и новым стилем классов в Python?
objectPython 2.
История от изучения Python трудный путь :
Оригинальное представление Python класса было сломано во многих серьезных отношениях. К тому времени, когда эта ошибка была признана, было уже слишком поздно, и они должны были поддержать это. Чтобы решить проблему, им нужен был стиль «новый класс», чтобы «старые классы» продолжали работать, но вы можете использовать новую, более правильную версию.
Они решили, что будут использовать слово «объект» в нижнем регистре как «класс», от которого вы наследуете, чтобы создать класс. Это сбивает с толку, но класс наследует от класса с именем «объект», чтобы создать класс, но на самом деле это не объект, а класс, но не забывайте наследовать от объекта.
Также просто для того, чтобы вы знали, в чем разница между классами нового стиля и классами старого стиля, это то, что классы нового стиля всегда наследуются от objectкласса или от другого класса, унаследованного от object:
class NewStyle(object):
pass
Другой пример:
class AnotherExampleOfNewStyle(NewStyle):
pass
В то время как базовый класс старого стиля выглядит так:
class OldStyle():
pass
И дочерний класс старого стиля выглядит так:
class OldStyleSubclass(OldStyle):
pass
Вы можете видеть, что базовый класс старого стиля не наследуется ни от какого другого класса, однако классы старого стиля могут, конечно, наследовать друг от друга. Наследование от объекта гарантирует, что определенная функциональность доступна в каждом классе Python. Новые классы стиля были введены в Python 2.2
objectне так уж и запутан, и на самом деле он довольно стандартный. Smalltalk имеет корневой класс с именем Objectи корневой метакласс Class. Почему? Потому что, так же как Dogи класс для собак, Objectэто класс для объектов и Classкласс для классов. Java, C #, ObjC, Ruby и большинство других основанных на классах ОО-языков, которые люди используют сегодня и которые имеют корневой класс, используют в Objectкачестве имени некоторые вариации, а не только Python.
Да, это исторически . Без этого он создает класс в старом стиле.
Если вы используете type()объект старого стиля, вы просто получаете «экземпляр». На объекте нового стиля вы получаете его класс.
type()класс старого стиля, вы получите «classobj» вместо «type».
Синтаксис оператора создания класса:
class <ClassName>(superclass):
#code follows
В отсутствие каких-либо других суперклассов, от которых вы конкретно хотите наследовать, superclassвсегда должно быть object, что является корнем всех классов в Python.
objectтехнически является корнем классов "нового стиля" в Python. Но классы нового стиля сегодня так же хороши, как и единственный стиль занятий.
Но если вы не используете слово явно objectпри создании классов, то, как уже упоминалось, Python 3.x неявно наследуется от objectсуперкласса. Но я думаю, что явное всегда лучше, чем неявное (ад)