为什么getattr()比自己慢了很多.__ dict __。get()?
以下示例来自Python 2.7上的REST数据库驱动程序。为什么getattr()比自己慢了很多.__ dict __。get()?
在下面的__setattr__
方法,如果我使用注释getattr()
线,它降低了从600个RPS的对象实例化性能230
为什么getattr()
比在这种情况下self.__dict__.get()
这么慢得多?
class Element(object):
def __init__(self, client):
self._client = client
self._data = {}
self._initialized = True
def __setattr__(self, key, value):
#_initialized = getattr(self, "_initialized", False)
_initialized = self.__dict__.get("_initialized", False)
if key in self.__dict__ or _initialized is False:
# set the attribute normally
object.__setattr__(self, key, value)
else:
# set the attribute as a data property
self._data[key] = value
总之:因为getattr(foo,bar)
does the same thing as foo.bar
,这不是刚刚访问__dict__
财产同样的事情(一开始,getattr
必须选择合适的__dict__
,但有很多更多的事情)。
详细信息包含在或关联到这里:http://docs.python.org/reference/datamodel.html(搜索“getattr”)。
@bereal:你需要重新阅读东西。 foo .__ dict __。get()的必要操作是getattr()的一个真子集。 – bukzor 2012-03-20 17:12:50
@bereal请记住,python字节码不对应于原始操作。你可以有非常少量的字节码来调用一个非常复杂的函数,而一个简单的表达式可以产生更多的字节码。另外,bukzor说的是正确和相关的。 – Marcin 2012-03-20 17:17:42
@bereal这并不能证明'foo .__ dict__'与getattr(foo,'__dict __')'相同,因为可以调用'getattr(foo,'__ dict __')'来提高效率比取消引用任意属性。 – Marcin 2012-03-20 17:35:30
另一方面,如果你有这样的性能差异,请在本地变量中缓存'self .__ dict__' - 即使只有两次访问它。 ('__setattr__'开头的'dict_ = self .__ dict__') – jsbueno 2012-03-20 17:45:40