使用Perl6处理大文本文件,速度太慢。(2014-09)

问题描述 投票:5回答:2

https://github.com/yeahnoob/perl6-perf中的代码宿主,如下:

use v6;

my $file=open "wordpairs.txt", :r;

my %dict;
my $line;

repeat {
    $line=$file.get;
    my ($p1,$p2)=$line.split(' ');
    if ?%dict{$p1} {
        %dict{$p1} = "{%dict{$p1}} {$p2}".words;
    } else {
        %dict{$p1} = $p2;
    }
} while !$file.eof;

当“ wordpairs.txt”较小时运行良好。

但是,当“ wordpairs.txt”文件大约为140,000行(每行,两个单词)时,它运行的非常慢。即使运行20秒,它也无法完成。

这是什么问题?代码中是否有错误?感谢任何人的帮助!

以下内容已于2014-09-04添加,感谢SE Answers和IRC @ freenode#perl6的许多建议

代码(目前为2014-09-04):

my %dict;
grammar WordPairs {
token word-pair { (\S*) ' ' (\S*) "\n" }
token TOP { <word-pair>* }
}
class WordPairsActions {
method word-pair($/) { %dict{$0}.push($1) }
}
my $match = WordPairs.parse(slurp, :actions(WordPairsActions));
say ?$match;

运行时间成本(目前):

$ time perl6 countpairs.pl wordpairs.txt
True
The pairs count of the key word "her" in wordpairs.txt is 1036

real    0m24.043s
user    0m23.854s
sys     0m0.181s

$ perl6 --version
This is perl6 version 2014.08 built on MoarVM version 2014.08

此测试的时间性能目前尚不合理(因为相同的Perl 5代码仅花费约160ms),但比我原来的旧Perl6代码要好得多。 :)

PS。整个过程,包括原始测试代码,补丁和示例文本,都在github上。

text large-files perl6 raku
2个回答
3
投票

我已经使用包含10,000行的文件,使用与Christoph的代码非常相似的代码对其进行了测试。大约需要15秒,这比Perl 5慢得多。我怀疑代码很慢,因为该代码使用的某些东西并未像Rakudo和MoarVM的其他部分最近所看到的那样进行优化。我敢肯定,随着速度的变慢,人们的注意力将在接下来的几个月中大大提高代码的性能。

[当尝试确定为什么某些Perl 6代码慢时,我建议使用--profile在MoarVM上运行perl6,以查看它是否有助于您找到瓶颈。不幸的是,使用此代码,它将指向rakudo内部,而不是您可以改进的任何地方。

值得在irc.freenode.net上与#perl6进行交谈,因为他们将具备提供替代解决方案的知识,并且将来能够提高其性能。


2
投票

Rakudo并非以其出色的性能而闻名。

使用更多惯用的代码可能会或可能不会有帮助:

my %dict;
for open('wordpairs.txt', :r).lines {
    my ($key, @words) = .words;
    push %dict{$key}, @words;
}

您还可以检查其他后端(Rakudo在MoarVM,Parrot和JVM上运行,以查看它是否到处都同样慢。


知道它是IO还是处理速度很慢,例如通过],这很有趣。

my %dict;

say 'start IO';
my @lines = eager open('wordpairs.txt', :r).lines;
say 'done IO';

say 'start processing';
for @lines { ... }
say 'done processing';

[我相信,如果您想自己研究问题,也可以使用探查器。

© www.soinside.com 2019 - 2024. All rights reserved.