В чем причина рекурсии?

На разницу между __getattr__ vs __getattribute__ есть несколько хороших примеров __getattr__ а также _getattribute__,

Почему __getattribute__ звонили 19 раз - после кода? Хорошо - это рекурсия... но почему?

class Count(object):

    def __init__(self,mymin,mymax):
        self.mymin=mymin
        self.mymax=mymax
        self.current=None

    def __getattr__(self, item):
            self.__dict__[item]=0
            return 0

    def __getattribute__(self, item):
        print("__getattribute__: ", item)          # only this line is new!!!!
        if item.startswith('cur'):
            raise AttributeError
        return object.__getattribute__(self,item)
        # or you can use ---return super().__getattribute__(item)
        # note this class subclass object

obj1 = Count(1,10)
print(obj1.mymin)
print(obj1.mymax)
print(obj1.current)
print("end")

Выход:

__getattribute__:  mymin
1
__getattribute__:  mymax
10
__getattribute__:  current
__getattribute__:  __dict__
0
end
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__
__getattribute__:  __class__

1 ответ

В CPython 3.7 единственный способ воспроизвести вашу проблему - это поставить точку останова и отладить ваш код.

Итак, несколько звонков Count.__getattribute__ скорее всего, вызвано чем-то другим (в моем случае: отладчиком), который пытается получить доступ к вашим атрибутам класса.

Для записи, вот трассировка, когда я запускаю ваш код обычным способом:

__getattribute__:  mymin
1
__getattribute__:  mymax
10
__getattribute__:  current
__getattribute__:  __dict__
0
end

Обратите внимание, что трассировка исключений не отображается, даже если obj1.current Доступ Это специфическое поведение, которое я не могу объяснить.

Другие вопросы по тегам