Чтение строк файла в хеш-параллель в Perl - PullRequest
0 голосов
/ 09 декабря 2018

У меня тысячи файлов.Моя цель - вставить строки этих файлов в хеш (большое количество этих строк повторяется).Сейчас я перебираю массив файлов и для каждого файла открываю его и делю строку (потому что каждая строка имеет следующий формат: <path>,<number>).Затем я вставляю в хеш %paths.Также каждую строку я записываю в один основной файл (пытаясь сэкономить время путем объединения).

Часть моего кода:

open(my $fh_main, '>', "$main_file") or die;
foreach my $dir (@dirs)
{
    my $test = $dir."/"."test.csv";
    open(my $fh, '<', "$test") or die;
    while (my $row = <$fh>)
    {
        print $fh_main $row;
        chomp($row);
        my ($path,$counter) = split(",",$row);
        my $abs_path = abs_path($path);
        $paths{$abs_path} += $counter;
    }
    close ($fh);
}
close ($fh_main);

Из-за большого количества файлов я хотел бы разбитьитерация не менее половины.Я подумал об использовании модуля Parallel::ForkManager ( link ), чтобы параллельно вставлять файлы в хеш A и в хеш B (если возможно, то более двух хешей).Затем я могу объединить эти два (или более) хешей в один основной хеш.Не должно быть проблемы с памятью (потому что я работаю на машине, у которой нет проблем с памятью).Я прочитал дезактивацию, но каждая попытка не удалась, и каждая итерация выполнялась отдельно.Я хотел бы увидеть первоначальный пример, если я должен решить эту проблему.Кроме того, я хотел бы услышать другое мнение о том, как реализовать это более понятным и мудрым способом.

Редактировать : возможно, я не понял, что именно делает модуль.Я хотел бы создать разветвление в сценарии, чтобы одна половина файлов была собрана процессом 1, а другая половина - процессом 2. Первая из них завершит запись в файл, а другая прочитаетот него.Возможно ли реализовать?Это уменьшит время выполнения?

1 Ответ

0 голосов
/ 10 декабря 2018

Попробуйте MCE :: Map .Он автоматически соберет выходные данные подпроцессов в список, который в вашем случае может быть хешем.Вот некоторый непроверенный псевдокод:

use MCE::Map qw[ mce_map ];

# note that MCE passes the argument via $_, not @_
sub process_file {
   my $file = $_;
   my %result_hash;
   ... fill hash ...
   return %result_hash
}

my %result_hash = mce_map  \&process_file \@list_of_files
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...