Создание неизменяемых типов в Python с помощью __new __ () - PullRequest
1 голос
/ 26 ноября 2011

Мой вопрос довольно прост, у меня есть:

class upperstr(str):
    def __new__(cls, arg):
        return str.__new__(cls, str(arg).upper())

Почему, если мой метод __new__() напрямую использует экземпляр неизменяемого типа (str), экземпляры моего нового типа (upperstr)являются изменяемыми?

>>> s = str("text")
>>> "__dict__" in dir(s)
False
>>> s = upperstr("text")
>>> "__dict__" in dir(s)
True

На каком этапе интерпретатор устанавливает атрибут __dict__ в значения upperstr, если я переопределяю только метод __new __ ()?

Спасибо!

1 Ответ

7 голосов
/ 26 ноября 2011

Все пользовательские классы в Python по умолчанию имеют атрибут __dict__(), даже если вы вообще ничего не перезаписываете:

>>> x = object()
>>> x.__dict__
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: 'object' object has no attribute '__dict__'
>>> class MyObject(object):
...     pass 
... 
>>> x = MyObject()
>>> x.__dict__
{}

Если вы не хотите, чтобы класс нового стиля имел __dict__, используйте __slots__ ( документация , связанный поток SO ):

>>> class MyObject(object):
...     __slots__ = []
... 
>>> x = MyObject()
>>> x.__dict__
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: 'MyObject' object has no attribute '__dict__'
...