作者keitheis (无)
看板Python
标题Re: [问题] List扩编的处理速度...
时间Thu Apr 30 01:53:42 2009
※ 引述《sbrhsieh (sbr)》之铭言:
: 请问你测试的 Python 版本是?
: 依照上述的码来说,依照 Python 2.5.4 内附的 timeit module 的设计来看,test2
: 与 test3 重复执行多次,会导致 testit module loaded 後 al 参考的 list object
: 一直作串接动作而变长(长度超过 100M)。
: 重复跑 test2 与 test3 会比 test1 多许多记忆体配置与 memory copy 的操作,
: 我不认为你跑出来的量测结果是合理的(test2/test3 应该比 test1 慢上许多)。
: 是否你使用的 timeit 与 Python 2.5.4 内附的版本不同?
真的也 XD
我是用 Python 2.5.4 内附的 timeit
Python 2.5.4 (r254:67917, Dec 23 2008, 14:57:27)
[GCC 4.0.1 (Apple Computer, Inc. build 5363)] on darwin
不太了解你说 timeit module 的设计是指?
只是我原来的 code 本身就有问题: global is evil XD
先来看看原来错误的地方
我们加上
run_print_len = '''
import sys
import testit
print >> sys.stderr, 'len(al):', len(testit.al), 'len(bl):', len(testit.bl)
'''
...(原来的code)
if __name__ == '__main__':
...(原来的code)
pl = timeit.Timer(run_print_len) # 新增这两行
pl.timeit(number=1) #
得到
% python2.5 testit.py
0.00002924 sec/pass
0.00002564 sec/pass
0.00002465 sec/pass
len(al): 200001000 len(bl): 1000
可以看到 al list 的长度非常之长,都快跟我一样长了 XD (误)
因为每次对 testit.al 所作的改变都会继续被下一个 test 使用
这样的测试造成 al 在每个 test 的长度都不同
可能造成测试的不准确
如 sbr 所述,记忆体可能需要重新配置之类的 (不过在我的环境好像没有影响?)
修正後 (syntax hilight 版
http://dpaste.com/hold/39347/ ):
import timeit
run_test1 = '''
import testit
al, bl = testit.generate_albl()
al = testit.test1(al, bl)
'''
run_test2 = '''
import testit
al, bl = testit.generate_albl()
al = testit.test2(al, bl)
'''
run_test3 = '''
import testit
al, bl = testit.generate_albl()
al = testit.test3(al, bl)
'''
run_print_len = '''
import sys
import testit
al, bl = testit.generate_albl()
print >> sys.stderr, 'len(al):', len(al), 'len(bl):', len(bl)
'''
def generate_albl():
al = [1]*1000
bl = [999]*1000
return al, bl
def test1(al, bl):
al = al + bl
return al
def test2(al, bl):
al.extend(bl)
return al
def test3(al, bl):
al += bl
return al
if __name__ == '__main__':
times = 100000
t1 = timeit.Timer(run_test1)
print "%.8f sec/pass" % (t1.timeit(number=times)/times)
t2 = timeit.Timer(run_test2)
print "%.8f sec/pass" % (t2.timeit(number=times)/times)
t3 = timeit.Timer(run_test3)
print "%.8f sec/pass" % (t3.timeit(number=times)/times)
pl = timeit.Timer(run_print_len)
pl.timeit(number=1)
得
% python2.5 testit.py
0.00005440 sec/pass
0.00004385 sec/pass
0.00004388 sec/pass
len(al): 1000 len(bl): 1000
感谢 sbr 指正
--
keitheis ")
--
※ 发信站: 批踢踢实业坊(ptt.cc)
◆ From: 122.121.154.38
※ 编辑: keitheis 来自: 122.121.154.38 (04/30 01:57)