本文介绍了在新式类中替换 __str__的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在转换旧的 Python 代码并用新样式的类替换了一些类.问题是这破坏了替换 __str__ 的行为,我不知道为什么.

I'm converting old Python code and replaced some classes with new style classes. The problem is that this broke the behavior of replacing __str__ and I have no idea why.

class OldStyle():
    def __str__(self):
        return 'original'

old = OldStyle()
print old
old.__str__ = lambda: 'modified'
print old


class NewStyle(object):
    def __str__(self):
        return 'original'

new = NewStyle()
print new
new.__str__ = lambda: 'modified'
print new

我预料到了

original
modified
original
modified

但是我得到了

original
modified
original
original

也就是说,__str__ 在新样式中没有被正确替换.打印 new.__str__ 正确返回新的 lambda,但 str(new) 仍然没有调用它.我以为是一些方法查找缓存问题,但即使之前从未打印过该对象,也会发生这种情况.

That is, __str__ was not correctly replaced in the new style. Printing new.__str__ returns the new lambda correctly, but str(new) still doesn't call it. I thought it was some method lookup caching problem, but this happens even if the object was never printed before.

为什么会这样?我从来没有听说过这种行为差异,它只发生在 __str__ 中,其他方法替换得很好.

Why does that happen? I have never heard about this behavior difference and it only happens with __str__, other methods are replaced fine.

推荐答案

这在 特殊方法名称.具体:

例如,如果一个类定义了一个名为__getitem__的方法,而x是这个类的一个实例,那么x[i]大致相当于x.__getitem__(i) 用于旧式类,type(x).__getitem__(x, i) 用于新式类.

我相信这使得新式类在这些操作方面的效率更高一些,因为对于旧式类,python 被迫查找属性,然后使用新式类调用该属性,python 可以将它作为 C 结构的一部分在某处引用,有效地将查找和调用推入本机 C 代码.例如:

I believe that this allows new-style classes to be a little more efficient in terms of these operations because with the old style classes, python was forced to look up the attribute and then call the attribute, with new-style classes, python can just reference it as part of a C struct somewhere effectively pushing the lookups and calls into native C code. For example:

class Foo:
    def __add__(self,other):
        return 4 + other

class Bar(object):
    def __add__(self,other):
        return 4 + other

import timeit
print timeit.timeit('f + 5','from __main__ import Foo; f = Foo()')
print timeit.timeit('b + 5','from __main__ import Bar; b = Bar()')

对我来说(python2.7.3,OS-X 10.5.8),新式类几乎快了 4 倍!

For me (python2.7.3, OS-X 10.5.8), the new-style class is almost 4 times faster!

2.27801704407
0.602614879608

这篇关于在新式类中替换 __str__的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

08-20 04:43