Я ищу способ считать входной файл и распечатать только избранные строки к выходному файлу в Perl. Строки, которые я хочу распечатать к выходному файлу, с которого все начинают xxxx.xxxx.xxxx
, где x
буквенно-цифровой знак (периоды являются периодами, не подстановочными знаками). Строки все не имеют того же окончания, если это имеет значение. Я думаю что-то как следующее (условие if
оператор - все, что действительно отсутствует насколько я могу сказать).
open(IN, "<$csvfile");
my @LINES = <IN>;
close(IN);
open(OUT, ">$csvnewfile");
print OUT @LINES if ([line starts with xxxx.xxxx.xxxx]);
close(OUT);
Заранее спасибо!
Вот вариант получше способ прокрутки ваших строк. Это позволяет избежать загрузки всего входного файла в память сразу:
use strict;
use warnings;
open my $fhi, '<', $csvfile or die "Can not open file $csvfile: $!";
open my $fho, '>', $csvnewfile or die "Can not open file $csvnewfile: $!";
while (<$fhi>) {
print $fho $_ if m/^ \w{4} \. \w{4} \. \w{4} /x;
}
close $fho;
close $fhi;
Имейте в виду, что класс символов \ w
также включает символы подчеркивания. Чтобы избежать подчеркивания:
print $fho $_ if m/^ [a-z\d]{4} \. [a-z\d]{4} \. [a-z\d]{4} /xi;
Советы по стилю:
open
close
на handle, открытом для записиСм. ниже:
#! /usr/bin/perl
use warnings;
use strict;
die "Usage: $0 old new\n" unless @ARGV == 2;
my($csvfile,$csvnewfile) = @ARGV;
open my $in, "<", $csvfile or die "$0: open $csvfile: $!";
open my $out, ">", $csvnewfile or die "$0: open $csvnewfile: $!";
while (<$in>) {
print $out $_ if /^\w{4}\.\w{4}\.\w{4}/;
}
close $out or warn "$0: close $csvnewfile: $!";
if ($_ =~ m/^\w{4}\.\w{4}\.\w{4}/i)
Я думаю. Мой perl немного заржавел.
Если вы не возражаете, оставьте его в качестве вкладки командной строки 1:
perl -ne "print if /^.{4}[.].{4}[.].{4}/" csvfile.csv > csvnewfile.csv
From perlfaq5 ответ на Как мне изменить, удалить или вставить строку в файл или добавить в начало файла?
Основная идея вставки, изменения или удаления строка из текстового файла включает чтение и печать файла до точки, в которой вы хотите внести изменение, внесение изменений, затем чтение и печать остальной части файла. Perl не предоставляет произвольный доступ к строкам (тем более, что разделитель входных записей, $ /, изменяемый), хотя такие модули, как Tie :: File, могут подделывать его.
Программа Perl для выполнения этих задач принимает базовую форму открытия файла, печати его строк и последующего закрытия файла:
open my $in, '<', $file or die "Can't read old file: $!";
open my $out, '>', "$file.new" or die "Can't write new file: $!";
while( <$in> )
{
print $out $_;
}
close $ out; В этой базовой форме добавьте части, которые вы нужно вставить, изменить или удалить строки.
Чтобы добавить строки в начало, распечатайте эти строки перед входом в цикл, который печатает существующие строки.
open my $in, '<', $file or die "Can't read old file: $!";
open my $out, '>', "$file.new" or die "Can't write new file: $!";
print $out "# Add this line to the top\n"; # <--- HERE'S THE MAGIC
while( <$in> )
{
print $out $_;
}
close $ out; Чтобы изменить существующие строки, вставьте код для изменения строк внутри цикла while. В этом случае код находит все версии «perl» в нижнем регистре и переводит их в верхний регистр.Это происходит для каждой строки, поэтому убедитесь, что вы должны делать это на каждой строке!
open my $in, '<', $file or die "Can't read old file: $!";
open my $out, '>', "$file.new" or die "Can't write new file: $!";
print $out "# Add this line to the top\n";
while( <$in> )
{
s/\b(perl)\b/Perl/g;
print $out $_;
}
close $ out; Чтобы изменить только определенную строку, может быть использован номер строки ввода $. Сначала прочтите и распечатайте строки до той, которую вы хотите изменить. Затем прочтите единственную строку, которую вы хотите изменить, измените ее и распечатайте. После этого прочтите остальные строки и распечатайте их:
while( <$in> ) # print the lines before the change
{
print $out $_;
last if $. == 4; # line number before change
}
my $line = <$in>;
$line =~ s/\b(perl)\b/Perl/g;
print $out $line;
while( <$in> ) # print the rest of the lines
{
print $out $_;
}
Чтобы пропустить строки, используйте элементы управления циклом. Следующий в этом примере пропускает строки комментариев, а последний останавливает всю обработку, когда встречает либо END , либо DATA .
while( <$in> )
{
next if /^\s+#/; # skip comment lines
last if /^__(END|DATA)__$/; # stop at end of code marker
print $out $_;
}
Сделайте то же самое для удаления определенной строки, используя next, чтобы пропустить строки, которые вы не хотите отображать в выводе. В этом примере пропускается каждая пятая строка:
while( <$in> )
{
next unless $. % 5;
print $out $_;
}
Если по какой-то нечетной причине вы действительно хотите увидеть весь файл сразу, а не обрабатывать построчно, вы можете пропустить его (при условии, что вы можете уместить весь файл целиком). вещь в памяти!):
open my $in, '<', $file or die "Can't read old file: $!"
open my $out, '>', "$file.new" or die "Can't write new file: $!";
my @lines = do { local $/; <$in> }; # slurp!
# do your magic here
print $out @lines;
С этим тоже могут помочь такие модули, как File :: Slurp и Tie :: File. Однако по возможности избегайте чтения всего файла сразу. Perl не вернет эту память операционной системе до завершения процесса.
Вы также можете использовать однострочники Perl для изменения файла на месте. Следующее изменяет все «Фред» на «Барни» в inFile.txt, перезаписывая файл новым содержимым. С переключателем -p Perl оборачивает цикл while вокруг кода, который вы указываете с помощью -e, а -i включает редактирование на месте. Текущая строка находится в $ . С -p Perl автоматически печатает значение $ в конце цикла. См. Perlrun для более подробной информации.
perl -pi -e 's/Fred/Barney/' inFile.txt
Чтобы сделать резервную копию inFile.txt, укажите для добавления -ia расширение файла:
perl -pi.bak -e 's/Fred/Barney/' inFile.txt
Чтобы изменить только пятую строку, вы можете добавить тест, проверяющий $., номер строки ввода, а затем выполнять операцию только после прохождения теста:
perl -pi -e 's/Fred/Barney/ if $. == 5' inFile.txt
Чтобы добавить строки перед определенной строкой вы можете добавить строку (или строки!) до того, как Perl напечатает $ _:
perl -pi -e 'print "Put before third line\n" if $. == 3' inFile.txt
Вы даже можете добавить строку в начало файла, поскольку текущая строка печатается в конце цикла:
perl -pi -e 'print "Put before first line\n" if $. == 1' inFile.txt
Чтобы вставить строку после уже существующей в файле строки, используйте переключатель -n. Это похоже на -p, за исключением того, что он не печатает $ _ в конце цикла, поэтому вам придется сделать это самостоятельно. В этом случае сначала напечатайте $ _, а затем напечатайте строку, которую вы хотите добавить.
perl -ni -e 'print; print "Put after fifth line\n" if $. == 5' inFile.txt
Чтобы удалить строки, распечатайте только те, которые вам нужны.
perl -ni -e 'print unless /d/' inFile.txt
... or ...
perl -pi -e 'next unless /d/' inFile.txt
с использованием grep
grep "^\w\{4\}\.\w\{4\}\.\w\{4\}\b" file
perl -ne 'print if /^\w{4}\.\w{4}\.\w{4}\b/' file > newfile.csv