乐趣区

关于perl:vim中perl与python处理文本的性能比较

终于想起账号 -_-!!

vim 中 perl 与 python 解决文本的性能比拟

又是一天不务正业, 本想把手上的小我的项目推进一步的,
后果却迷失在了

如何给 vim 加上 XXX HACK NOTE 等标签高亮显示上
为了 hack todo-vim 插件(大小字查找问题), 又花了大量工夫在 vimscript+ 内置 perl 交互上

在 [2.] 这步, 查到一篇也是很有帮忙的一篇 用 vim 解决巨量数据的文章. 其中有 python 也有 perl 也有 vimscript,
通过他的实际, python 比 perl(在 vIM 里)解决文本快得多.
作为 python / perl 双修修士, 有点不服气, 认为不可能有 3 倍差距.
因而, 也花了工夫重做了一遍 benchmark

详情

1. 生成测试用文件

perl -e 'open my $f,">","test.txt"; for($i=0;$i<100000;$++) {print $f"\"value\"\n{\n    \"wave\"\n    \"wave\"\n    \"wave\"\n    \"wave\"\n}\n\n";}'

文件 879992 行, 6269943 字节

2. 编写 vim 代码

内容如下

function! test#pythonmod1()
    " 无正则 形式
    let start_time = localtime()
    echo("开始解决...")
python3 << EOF
import vim, re
vimBuffer = vim.current.buffer
num = 0
c = 0
l = 0
while l < len(vimBuffer):
    if vimBuffer[l] == '"value"':
        num = 0
    elif vimBuffer[l] == '"wave"':
        vimBuffer[l] = '"wave' + str(num) + '"'
        c += 1
        num += 1
    l += 1
vim.command("let c=" + str(c))
EOF
"redraw!
echo("实现!\n 共替换" . c ."行 \n 耗时:" . (localtime()-start_time) . "秒")
endfunction

function! test#pythonmod()
    " 正则版本
    let start_time = localtime()
    echo("开始解决...")
python3 << EOF
import vim, re
vimBuffer = vim.current.buffer
num = 0
c = 0
l = 0
p_value = re.compile(".*value.*")
p_wave = re.compile(".*wave.*")
while l < len(vimBuffer):
  if p_value.match(vimBuffer[l]):
    num = 0
  elif p_wave.match(vimBuffer[l]):
    vimBuffer[l] = '"wave' + str(num) + '"'
    c += 1
    num += 1
  l += 1
vim.command("let c=" + str(c))
EOF
"redraw!
echo("实现!\n 共替换" . c ."行 \n 耗时:" . (localtime()-start_time) . "秒")
endfunction

function! test#perlmod1()
    " 无正则版本
    let start_time = localtime()
    echo("开始解决...")
perl << EOF   
    $lnum = 1;
    $num = 0;
    $c = 0;
    while ($lnum <= $curbuf->Count()) {if ($curbuf->Get($lnum) eq '"value"') {$num = 0;}
        elsif ($curbuf->Get($lnum) =~ '"wave"') {$curbuf->Set($lnum, '"wave' . $num . '"');
            $c += 1;
            $num += 1;
        }
        $lnum += 1
    }
    VIM::DoCommand("let c=" . $c);
EOF
"redraw!
echo("实现!\n 共替换" . c ."行 \n 耗时:" . (localtime()-start_time) . "秒")
endfunction

function! test#perlmod()
    " 正则版本
    let start_time = localtime()
    echo("开始解决...")
perl << EOF   
    $lnum = 1;
    $num = 0;
    $c = 0;
    while ($lnum <= $curbuf->Count()) {if ($curbuf->Get($lnum) =~ /value/) {$num = 0;}
        elsif ($curbuf->Get($lnum) =~ /wave/) {$curbuf->Set($lnum, '"wave' . $num . '"');
            $c += 1;
            $num += 1;
        }
        $lnum += 1
    }
    VIM::DoCommand("let c=" . $c);
EOF
"redraw!
echo("实现!\n 共替换" . c ."行 \n 耗时:" . (localtime()-start_time) . "秒")
endfunction

因为无奈应用 python2 版本, vim 只能运行 python3
python 版本

perl 版本

机器配置及操作系统

操作系统为节电配置

python 正则版本

首次运行

第二次

第三次

均匀工夫为 7.334 秒

python 非正则版本

首次运行

第二次

第三次

均匀工夫为: 6.667 秒

perl 正则版本

首次运行

第二次

第三次

均匀工夫为 6.667 秒

perl 非正则版本

首次运行

第二次

第三次

均匀工夫为 7.667 秒

论断

能够看出非正则版本 python 略快一些, 正则版本则是 perl 性能当先
所以, 在我这软硬件条件下, vim+perl/python 解决文本内容性能伯仲之间

ps: 原作者贴出的代码里, perl 版本是有调用 vim redraw, 而 python 没有调用, 我猜是性能差距的次要起源.
PS2:perl 文字处理应用正则性能好, 而 python 不应用正则性能高. 很有意思的

退出移动版