Чтение определенной строки из большого файла в Perl - PullRequest
8 голосов
/ 18 декабря 2011

Существует ли какой-либо быстрый и эффективный способ чтения определенных строк большого файла без загрузки его в память?

Я написал Perl-скрипт, который запускает много форков, и я хотел бы, чтобы они читали определенные строки из файла.

В данный момент я использую внешнюю команду:

sub getFileLine {
    my ( $filePath, $lineWanted ) = @_;
    $SIG{PIPE} = '_IGNORE_';
    open( my $fh, '-|:utf8', "tail -q -n +$lineWanted \"$filePath\" | head -n 1" );
    my $line = <$fh>;
    close $fh;
    chomp( $line );
    return $line;
}

Это быстро, и это работает - но, может быть, есть более "перламутровый" способ, такой же быстрый и эффективный, как этот?

Как вы знаете, создание процесса разветвления в Perl дублирует основную память процесса - поэтому, если основной процесс использует 10 МБ, разветвитель будет использовать как минимум столько же.

Моя цель состоит в том, чтобы максимально сократить использование памяти процессом (таким образом, основным процессом до запуска вилок). Вот почему я не хочу загружать весь файл в память.

Ответы [ 3 ]

17 голосов
/ 18 декабря 2011

Прежде чем идти дальше, важно понять, как работает fork. Когда вы fork выполняете процесс, ОС использует семантику копирование при записи , чтобы разделить объем памяти родительского и дочернего процессов; только объем памяти, который отличается между родителем и потомком, должен быть выделен отдельно.

Для чтения одной строки файла в Perl, есть простой способ:

open my $fh, '<', $filePath or die "$filePath: $!";
my $line;
while( <$fh> ) {
    if( $. == $lineWanted ) { 
        $line = $_;
        last;
    }
}

Используется специальная переменная $., которая содержит номер строки текущего дескриптора файла.

4 голосов
/ 18 декабря 2011

Взгляните на Tie :: File основной модуль.

0 голосов
/ 05 ноября 2012

Вам не нужно разветвляться.Как вы можете себе представить, чтение определенной строки из файла является достаточно распространенной операцией, поэтому один из 20k-модулей в CPAN уже делает это.быстро.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...