4

当我调用str()具有重载__getattribute__方法的对象时,它似乎并没有使用它,而是__str__直接调用。是否有其他一些我应该修改的功能或让它使用的方法__getattribute__?如果我直接重载__str__它会按预期运行,但这并不适合我的需求。

class A(object):
    def __getattribute__(self, attr):
        if attr == "__str__":
            return lambda: "Hello"
        return object.__getattribute__(self, attr)

x = A()

print(x)
print(str(x))
print(x.__str__())

输出:
< main .A object at 0x000001FDF7AEA760>
< main .A object at 0x000001FDF7AEA760>
你好

预期输出:
你好
你好
你好

4

1 回答 1

5

是的,这是记录在案的行为

由于通过语言语法或内置函数隐式调用而查找特殊方法时,仍可能绕过此方法。

这里:

对于自定义类,特殊方法的隐式调用只有在对象类型上定义时才能保证正常工作,而不是在对象的实例字典中

...

除了为了正确性而绕过任何实例属性之外,隐式特殊方法查找通常也会绕过__getattribute__()对象元类的方法......

...

至于为什么

以这种方式绕过__getattribute__()机制为解释器中的速度优化提供了很大的空间,但代价是处理特殊方法的一些灵活性(特殊方法必须在类对象本身上设置,以便解释器始终调用) .

于 2020-04-20T20:09:25.150 回答