V2EX = way to explore
V2EX 是一个关于分享和探索的地方
Sign Up Now
For Existing Member  Sign In
mrpzx001
V2EX  ›  PHP

PHP 跑 Python 比 Python 更快!

  •  1
     
  •   mrpzx001 · Dec 8, 2023 · 3966 views
    This topic created in 873 days ago, the information mentioned may be changed or developed.

    原文

    https://github.com/swoole/phpy/blob/main/docs/benchmark.md

    压力测试

    压测脚本中创建了一个 PyDict ,分别读写 PHP 代码和 Python 代码执行 1000 万次

    • PHP 版本PHP 8.2.3 (cli) (built: Mar 17 2023 15:06:57) (NTS)
    • Python 版本Python 3.11.5
    • 操作系统:Ubuntu 20.04
    • GCC 版本gcc version 9.4.0 (Ubuntu 9.4.0-1ubuntu1~20.04.2)

    请注意设需要构造一个 1000 万个元素的 HashTable,需要至少 2G 以上内存空间才可以运行此测试

    PHP

    <?php
    
    $dict = new PyDict();
    const COUNT = 10000000;
    
    $n = COUNT;
    $s = microtime(true);
    while ($n--) {
        $dict['key-' . $n] = $n * 3;
    }
    echo 'dict set: ' . round(microtime(true) - $s, 6) . ' seconds' . PHP_EOL;
    
    $c = 0;
    $n = COUNT;
    $s = microtime(true);
    while ($n--) {
        $c += $dict['key-' . $n];
    }
    echo 'dict get: ' . round(microtime(true) - $s, 6) . ' seconds' . PHP_EOL;
    

    Python

    import time
    
    my_dict = {}
    COUNT = 10000000
    
    n = COUNT
    start_time = time.time()
    
    
    for i in range(n):
        my_dict["key-" + str(i)] = i * 3
    
    elapsed_time = time.time() - start_time
    
    print(f"dict set: {elapsed_time:.6f} seconds")
    
    n = COUNT
    
    total = 0
    start_time_get = time.time()
    for i in range(n):
        total += my_dict["key-" + str(i)]
    
    elapsed_time_get = time.time() - start_time_get
    
    print(f"dict get: {elapsed_time_get:.6f} seconds")
    

    PHP 数组

    <?php
    
    ini_set('memory_limit', '2G');
    $dict = [];
    const COUNT = 10000000;
    
    $n = COUNT;
    $s = microtime(true);
    while ($n--) {
        $dict['key-' . $n] = $n * 3;
    }
    echo 'array set: ' . round(microtime(true) - $s, 6) . ' seconds' . PHP_EOL;
    
    $c = 0;
    $n = COUNT;
    $s = microtime(true);
    while ($n--) {
        $c += $dict['key-' . $n];
    }
    echo 'array get: ' . round(microtime(true) - $s, 6) . ' seconds' . PHP_EOL;
    

    结果对比

    (base) htf@swoole-12:~/workspace/python-php/docs/benchmark$ php dict.php 
    dict set: 4.663758 seconds
    dict get: 3.980076 seconds
    (base) htf@swoole-12:~/workspace/python-php/docs/benchmark$ php array.php 
    array set: 1.578963 seconds
    array get: 0.831129 seconds
    (base) htf@swoole-12:~/workspace/python-php/docs/benchmark$ python dict.py 
    dict set: 5.321664 seconds
    dict get: 4.969081 seconds
    (base) htf@swoole-12:~/workspace/python-php/docs/benchmark$
    

    Python 测试为基准:

    脚本名称 Set Get
    dict.php 114% 125%
    array.php 337% 599%
    • phpyPHP 代码写入 PyDict 的性能比原生 Python14%,读取性能高 25%
    • PHP 写入 PHP Array 的性能比 Python 写入 Dict237%,读取高出了近 500%

    其他

    phpy 这个项目已经进化到可以调用任何 python 内置常量、函数、模块,包括 print 、compile 、eval 、exec 等等,也就是说你完全可以用 php 的语法来写 python ,比如

    https://docs.python.org/zh-cn/3/library/ast.html#module-ast
    示例代码:print(ast.dump(ast.parse('x = 1'), indent=4))
    
    php 写法:
    $py = PyCore::import('builtins');
    $ast = PyCore::import('ast');
    $py->print($ast->dump($ast->parse('x = 1'), indent: 4));
    

    以上只是写着玩,phpy 的初衷是用 python 来弥补 php 生态上的不足,现在你可以用 php 来跑大模型了

    13 replies    2023-12-09 13:04:19 +08:00
    ersic
        1
    ersic  
       Dec 8, 2023
    可是今天韩天峰刚说了,损耗在 50%左右
    mrpzx001
        2
    mrpzx001  
    OP
       Dec 8, 2023
    @ersic 他昨天测试的时候用的是 debug 版的 php ,性能当然差了
    aogg
        3
    aogg  
       Dec 8, 2023
    能不能用 python 的库,比如 gui 界面之类的,还有大模型的类库
    aogg
        4
    aogg  
       Dec 8, 2023
    不能支持多线程的原理是什么
    tf2
        5
    tf2  
       Dec 8, 2023   ❤️ 1
    凡事编程语言跑分,python 一看到 for 就直接宣布比赛结束了。
    tf2
        6
    tf2  
       Dec 8, 2023
    另外
    my_dict["key-" + str(i)] = i * 3

    改成

    my_dict["key-%s"% i] = i * 3

    我这里会从 5.6 秒变 4.6 秒。
    tf2
        7
    tf2  
       Dec 8, 2023
    换成 my_dict[b"key-%d"% i] = i * 3 变成 3.6 秒。

    结论:字符串是个体力活。
    mrpzx001
        8
    mrpzx001  
    OP
       Dec 8, 2023
    @aogg 能,轻轻松松跑起来 chatglm3 ,gui 更不在话下了,可以看 example
    mrpzx001
        9
    mrpzx001  
    OP
       Dec 8, 2023
    @aogg 不是不能,大佬没空而已,说不定哪天兴致来了就支持了
    NoOneNoBody
        10
    NoOneNoBody  
       Dec 8, 2023
    试试
    my_dict = {f"key-{i}": i*3 for i in range(n)}
    ...
    total = sum(my_dict.values())
    我没环境测试

    最想不通在无需过滤的情况下,求 total 为什么要跑个 for 累加器,抓着痛处打?
    encro
        11
    encro  
       Dec 8, 2023
    没达到一个数量级差别的优化,意义都不大。。。。
    lisxour
        12
    lisxour  
       Dec 8, 2023
    numpy 这类的库不是有专门的优化嘛,这能打得过?
    crackidz
        13
    crackidz  
       Dec 9, 2023
    这不是比了个寂寞...一到 Python 代码里面速度不就一样了
    About   ·   Help   ·   Advertise   ·   Blog   ·   API   ·   FAQ   ·   Solana   ·   2916 Online   Highest 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 44ms · UTC 15:13 · PVG 23:13 · LAX 08:13 · JFK 11:13
    ♥ Do have faith in what you're doing.