Могу ли я использовать поиск и замену для вставки прогрессивного числа в Perl? - PullRequest
0 голосов
/ 07 апреля 2011

Прошу прощения, если этот вопрос звучит глупо, но я много искал и сейчас большую часть дня я работаю над довольно тривиальной задачей.

Мне нужно вставить последовательно пронумерованные идентификаторы в текстовый файл. В файле уже есть метки-заполнители, так что я бы предпочел работать с поиском и заменой. Лучшее, что я мог сделать, было следующее:

#!/usr/bin/perl
my $counter = 1;
my $oldID = "docID=\"";
my $newID = "docID=\"14$counter"; #should the return the IDs 141, 142, 143 ...

open (FILE, "file.txt") || die $!;
@content = <FILE>;

foreach (@content){
s/$oldID/$newID/;
$counter++;
}

open (OUT, ">file_ID.txt") || die $!;
print OUT @content;
close OUT;
close(FILE);

print = "$counter" #this is to test if the counter is working.

это находит и заменяет docID = "". К сожалению, он заменяет все вхождения docID на 141.

Я бы предположил, что это не сработает, потому что все случаи заменяются сразу, и счетчик никогда не получает шанса стать больше. Это, однако, не выглядит правдоподобным, если я вижу, что $ counter становится слишком большим. Это ровно в 12 раз больше случаев docID.

Мне кажется, мне нужно получить perl, чтобы заменить только один случай использования docID, затем поднять счетчик и сделать это в цикле до конца документа.

Может ли кто-нибудь помочь мне, пожалуйста? Я был бы очень признателен

Thx

Iulius

Ответы [ 3 ]

3 голосов
/ 07 апреля 2011
open my $in, '<', 'file.txt' or die "$! opening input";
open my $out, '>', 'file_ID.txt' or die "$! opening output";

my $counter = 141;

while (<$in>) {
    s/docID="/q{docID="} . $counter++ /eg;
    print $out $_;
}

Использует s///e для замены и приращения счетчика при обнаружении экземпляров, а также обрабатывает файл построчно, а не считывает его все в память и записывает все обратно, потому что нет реальной причинысделать это.

2 голосов
/ 07 апреля 2011

регулярные выражения perl поддерживают «eval», так что вы можете сделать:

s/$oldId/"docid=\"" . $newId++ . "\""/e

, где / e - это часть eval, которая уклоняется от замены при каждом вызове.

1 голос
/ 07 апреля 2011

В своем коде вы можете переместить переменную $ newID внутри цикла for:

foreach (@content){
    my $newID = "docID=\"14$counter";
    s/$oldID/$newID/;
    $counter++;
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...