Если я правильно понимаю ваш вопрос, это может быть яснее с другими инструментами, чем регулярные выражения.Следующие слова сводят все пробелы между словами в один пробел.
Ввод qwwk.txt
(с добавлением одной строки)
..........
QWWK jhjh kljdfh jklh jskdhf jkh PQXY
lhj ah jh sdlkjh PQXY jha slkdjh
PQXY jh alkjh ljk
kjhaksj dkjhsd KWWQ
hahs dkj h PQXY
.........
KWWQ in mid line doesn't trigger: QWWK a PQXY b KWWQ c QWWK d PQXY e KWWQ
Команда perl qwwk.pl qwwk.txt
Выход
..........
QWWK jhjh kljdfh jklh jskdhf jkh
lhj ah jh sdlkjh jha slkdjh
jh alkjh ljk
kjhaksj dkjhsd KWWQ
hahs dkj h PQXY
.........
KWWQ in mid line doesn't trigger: QWWK a PQXY b KWWQ c QWWK d PQXY e KWWQ
Программа qwwk.pl
use strict; use warnings;
while(<>) { # for each line
my @out;
my @words=split; # get its words
for my $i (0..$#words) {
my $w=$words[$i];
my $active = ($i==0 && $w eq q(QWWK)) .. ($i==$#words && $w eq q(KWWQ));
# Keep track of where we are. See notes below.
push @out, $w unless $active and ($w eq q(PQXY));
# Save words we want to keep
} #foreach word
print join(q( ), @out), qq(\n); # Print the words we saved
} #foreach line
Ключ в том, чтоОператор триггера (..
) в назначении $active= FOO .. BAR
сохраняет свое состояние независимо от того, что происходит вокруг него.Это будет истинно от QWWK
в начале строки (($i==0 && $w eq q(QWWK))
) до KWWQ
в конце строки (($i==$#words && $w eq q(KWWQ))
), независимо от того, сколько строк вмешивается.
Как однострочный
perl -Mstrict -Mwarnings -ne 'my @out; my @words=split; for my $i (0..$#words) { my $w=$words[$i]; my $active = ($i==0 && $w eq q(QWWK)) .. ($i==$#words && $w eq q(KWWQ)); push @out, $w unless $active and ($w eq q(PQXY)); } print join(q( ), @out), qq(\n);' qwwk.txt
Разница здесь в том, что -n
обеспечивает цикл while(<>){}
, поэтому он не включен в скрипт -e
.(Плюс, теперь вы знаете, почему я использовал q()
и qq()
в автономной программе;).)