
Python 代码: import time a=time.time() i=0 for i in xrange(95550000): i +=100 i -=100 print i print time.time()-a
运行结果: 95549999 15.253000021
得到的不是 95550000 编译成了 Pyc 也一样的结果
但换成 Node.js 会快 100 倍都不止 var a=new Date(); var i; for(i = 0; i < 95550000; ++i) { i += 100; i -= 100; } console.log(i) console.log((new Date())-a)
结果: 95549999 0.21799993515
我试了 pypy,性能和 node.js 接近
1 koykoi 2016-04-02 15:01:29 +08:00 这种 hot spot 代码不正是 JIT 的优势吗 |
2 clino 2016-04-02 15:17:23 +08:00 nodejs 应该和 pypy 一样都用了 jit 吧? |
3 clino 2016-04-02 15:26:31 +08:00 我这里的结果是 -在循环里算两个+-耗时 15.1 秒 -在循环里算一个+耗时 9.89 秒 -循环里 pass 耗时 3.72 秒 |
4 BOYPT 2016-04-02 15:27:47 +08:00 大概是因为 python 里面的整数是 immutable 的对象,你这样的操作就是重复生成对象和回收对象,所以效率较低;大概使用 numbers 模块里面功能会有改善。 |
5 josephok 2016-04-02 16:01:50 +08:00 用 python3 试试 |
6 ikw 2016-04-02 16:09:22 +08:00 本来就应该是 9554999 的吧? python3 是: 95549999 10.84103798866272 |
7 Zzzzzzzzz 2016-04-02 16:09:46 +08:00 光这个 xrange 就得两三秒. 要改进性能的话把这段代码抽出来上 Cython , i = 0 前面加 cdef long, 秒变毫秒级. |
8 simon4545 OP python3 执行也是一样的,而且还要更久一点 有没有 jit 居然相差那么大 |
9 realpg PRO 1. python 内 xrange(3)的结果是 0,1,2 2. 这种场景就是 JIT 的性能强悍啊 realpg@TestingServer17:/tmp/demo$ python python.py 95549999 15.7798058987 realpg@TestingServer17:/tmp/demo$ pypy python.py 95549999 0.574637174606 realpg@TestingServer17:/tmp/demo$ /usr/local/php5/bin/php php.php 95550000 7.9244079589844 realpg@TestingServer17:/tmp/demo$ /usr/local/php7/bin/php php.php 95550000 3.8246450424194 python2.7 python.py 代码同楼主 php.php 代码 <?php $time_start = microtime(true); for ($i=0;$i<95550000;$i++) { $i+=100; $i-=100; } $time_end = microtime(true); $time = $time_end - $time_start; echo "{$i}\n{$time}\n"; |
10 slixurd 2016-04-02 19:21:49 +08:00 居然连 microbench 之类的工具都没用,在这裸写。。。。 |
11 bigtan 2016-04-02 19:24:52 +08:00 用 Python ,执行效率一般难以成为瓶颈,因为,他可以通过别的优化手段轻松的达到 C-level 的执行效率。 |
12 theoractice 2016-04-02 20:27:43 +08:00 @bigtan 42.7ns ?表示震惊 |
13 zhuangzhuang1988 2016-04-02 22:01:59 +08:00 没 jit 就得这么慢, 虽然里面有一些 intern 缓存优化。但是对这些纯计算的没啥鸟用。。 |
14 bigtan 2016-04-02 22:04:09 +08:00 @theoractice 有缓存的可能,你可以看 best case 。 42.7ns*24.87=1061.9ns ,不过也足够惊人的了。 |
15 est 2016-04-02 22:21:06 +08:00 其实 python 加减乘除不慢, for 比较慢。 |
16 mathgl 2016-04-02 22:30:28 +08:00 这种代码, jit 稍微优化一下就是常数了。 |
17 Zzzzzzzzz 2016-04-02 22:37:08 +08:00 @theoractice @bigtan 倒没那么夸张, Cython 现在对 range 和 xrange 有优化, 会直接转成循环, 以前那种 for i from 0<=i<95550000 的方言被废了, 然后默认的编译参数又是-O2, 直接把循环这部分给优化掉了,等于什么都没做直接给 i 赋值了 |
18 SlipStupig 2016-04-03 01:35:18 +08:00 每次+一次就是内存申请一次啊,而且你用 for 就变成了直接 sum 回快多了 sum(xrange(95550000)),时间明显减少太多了 3 function calls in 1.140 seconds Ordered by: standard name ncalls tottime percall cumtime percall filename:lineno(function) 1 0.000 0.000 1.140 1.140 test.py:1(<module>) 1 0.000 0.000 0.000 0.000 {method 'disable' of '_lsprof.Profiler' objects} 1 1.140 1.140 1.140 1.140 {sum} |
20 pynix 2016-04-03 04:27:50 +08:00 不可变对象,一直在申请和释放内存。 |
22 simon4545 OP @imn1 python 我是新手,你说的列表元组是指的是用[sum(x ) for i in range(59990000)]推导么? |
24 wizardforcel 2016-04-03 12:55:30 +08:00 via Android node 自带了 jit ,你用 xpcshell 试试。(逃 |
25 fullpowers 2016-04-03 14:23:34 +08:00 via Android 我智商捉急,求问为什么是 95549999 |
27 MrEggNoodle 2016-04-03 15:54:51 +08:00 @bigtan 看到你这个,我决定深入了解一下 cython 了。 |
28 simon4545 OP +1 cython |