我们正在做一些实验来比较类和命名元组中的访问时间,并观察到一些奇怪的事情。
import time
from collections import namedtuple as namedtuple
class myclass(object):
def __init__(self, _name, _dob, _value):
self.name = _name
self.dob = _dob
self.value = _value
randomperson1 = myclass( 'randomperson', 10102000, 10.45 )
person = namedtuple( 'person', 'name dob value' )
randomperson2 = person( 'randomperson', 10102000, 10.45)
在使用ipython的timeit时,观察到以下情况:
%timeit randomperson1.name,randomperson1.value,randomperson1.dob
10000000 loops, best of 3: 125 ns per loop
%timeit randomperson2.name,randomperson2.value,randomperson2.dob
1000000 loops, best of 3: 320 ns per loop
%timeit randomperson2[0],randomperson2[1],randomperson2[2]
10000000 loops, best of 3: 127 ns per loop
为什么通过字段名访问一个namedtuple比访问一个类的成员变量要慢得多?有什么方法可以加快速度吗?
答案 0 :(得分:3)
那是因为namedtuple
属性name, value, dob
不是实例上的简单属性。它们实际上变成了更复杂的东西
<强> collections.py 强>
_field_template = '''\
{name} = _property(_itemgetter({index:d}), doc='Alias for field number {index:d}')
'''
e.g。
dob = property(itemgetter(2), doc='Alias for field number 2')
因此,您可以看到其上有其他图层。创建namedtuple
的人决定他们希望以CPU效率为代价来保持内存效率的一致性。这就是原因。
当您创建自己的自定义类时,可以很容易地观察到这一点:
from operator import itemgetter
class CustomTuple(tuple):
my_attr = property(itemgetter(0))
test_tuple = CustomTuple([1])
现在衡量对test_tuple.my_attr
的访问权限。你应该得到几乎相同的结果。