我正在分析在一个句子中一起出现的词组的出现频率。
每组由 3 个单词组成,我们必须计算它们的频率。
示例:这是聚会的好时机,因为这是假期。
预期输出:
this is a - 2
is a good - 1
a good time - 1
等等。
我编写了一个运行良好的脚本,它打印频率并按降序对其进行排序。
它通过从文件中一次读取一行来工作。对于每一行,它将它们转换为小写,将其拆分为单个单词,然后从中形成一个数组。
然后,我们从左边开始一次选择 3 个单词,并不断形成一个存储出现次数的哈希值。完成后,我们移动数组中最左边的元素并重复,直到我们的数组包含超过 3 个单词。
问题更新:
问题是我想在一个包含超过 1000 万行的文件上使用这个脚本。
运行一些测试后,我观察到如果输入文件中的行数超过 400K,它将无法正常工作。
我怎样才能使这个脚本更有效地使用内存?
感谢 fxzuz 的建议,但现在我想让这个脚本适用于更大的文件 :)
#!/usr/bin/perl
use strict;
use warnings;
print "Enter the File name: ";
my $input = <STDIN>;
chomp $input;
open INPUT, '<', $input
or die("Couldn't open the file, $input with error: $!\n");
my %c;
while (my $line = <INPUT>) {
chomp $line;
my @x = map lc, split /\W+/, join "", $line;
while (@x>3) {
$c{"@x[0..2]"}++;
shift @x;
}
}
foreach $key (sort {$c{$b} <=> $c{$a}} keys %c) {
if($c{$key} > 20) {
print $key." - ".$c{$key}."\n";
}
}
close INPUT;
这很好用,它会按频率降序打印单词组。它只会打印那些出现超过 20 次的单词组。
现在,如何在包含超过 100 万或 1000 万行的文件上进行这项工作?
在 Linux 中使用 top 命令运行此脚本时,我还检查了 perl 的内存和 CPU 使用率,并观察到当脚本在由 400K 行组成的文件上运行时,CPU 使用率达到 100%,内存使用率接近 90%。
因此,让它与一个由 100 万行组成的文件一起工作是不可行的。因为perl进程会挂起。
我怎样才能让这段代码更有效地使用内存?