Если файлы не слишком велики для памяти, я бы выбрал решение TLP.Если они есть, вы можете немного изменить его и распечатать в файл, как он предлагает.Добавьте это перед while
(все непроверенные, ymmv, caveat programmer и т. Д.):
my $currentInFile = "";
my $currentOutFileHandle = "";
и измените тело while
с текущего if-else
на
if ($currentInFile ne $ARG) {
if (fileno($currentOutFileHandle)) {
if (!close($currentOutFileHandle)) {
# whatever you want to do if you can't close the previous output file
}
}
my $newOutFile = $ARG . ".tagged";
if (!open($currentOutFileHandle, ">", $newOutFile)) {
# whatever you want to do if you can't open a new output file for writing
}
}
if (...conditional from TLP...) {
# add more zeroes if the files really are that large :)
$lastkey = $1 . " " . sprintf("%0.10d", $.);
}
if (fileno($currentOutFileHandle)) {
print $currentOutFileHandle $lastkey . "\t" . $line;
}
else {
# whatever you want to do if $currentOutFileHandle's gone screwy
}
Теперь вы будете иметь тег foo.log.tagged для каждого файла foo.log, который вы его кормили;файл .tagged содержит в точности содержимое оригинала, но к каждой строке добавляется «0xNNNNNNNN LLLLLLLLLL \ t» (LLLLLLLLLL -> номер строки с нулевым отступом).sort(1)
на самом деле неплохо справляется с обработкой больших данных, хотя вы захотите взглянуть на аргумент --tevent-directory, если вы думаете, что он переполнит / tmp своими временными файлами, пока просматривает материал, который вы передаете.Что-то вроде этого должно помочь вам начать:
sort --output=/my/new/really.big.file --temporary-directory=/scratch/dir/on/roomy/partition *.tagged
Затем обрежьте теги, если хотите:
perl -pi -e 's/^[^\t]+\t//' /my/new/really.big.file
FWIW, я добавил номера строк, чтобы не беспокоиться о таких вещахсортировка строки 10 перед строкой 2, если их шестнадцатеричные ключи были идентичны - поскольку шестнадцатеричные числа являются основным критерием сортировки, мы не можем просто выполнить числовую сортировку.