Ответ 1
В соответствии с этим, super не разрешает неявные вызовы функций "hook", таких как __getattr__
. Я не уверен, почему это реализовано таким образом (вероятно, есть веская причина, и вещи уже запутывают достаточно, поскольку у супер-объекта есть пользовательские методы __getattribute__
и __get__
, как есть), но похоже, что это просто путь вещи есть.
Изменить: Похоже, что это сообщение немного очистило. Похоже, проблема заключается в том, что дополнительный слой косвенности, вызванный __getattribute__
, игнорируется при вызове функций неявно. Выполнение foo.x
эквивалентно
foo.__getattr__(x)
(Предполагая, что метод __getattribute__
не задан и x не находится в foo.__dict__
)
Однако это НЕ эквивалентно
foo.__getattribute__('__getattr__')(x)
Так как super возвращает прокси-объект, у него есть дополнительный слой косвенности, который заставляет вещи терпеть неудачу.
P.S. Проверка self.__dict__
в вашей функции __getattr__
совершенно не нужна. __getattr__
вызывается только в том случае, если атрибут еще не существует в вашем dict. (Используйте __getattribute__
, если вы хотите, чтобы он всегда вызывался, но тогда вы должны быть очень осторожны, потому что даже что-то простое, как if name in self.__dict__
, вызовет бесконечную рекурсию.