2016-10-11 2 views
0

У меня есть следующая командаудалить строки после шаблона в нескольких файлах

find ./ -type f -exec perl -pi -e 's/<pattern>//g' '{}' \; 

он хорошо работает и удалить шаблон, но как я могу удалить шаблон, строку он включен, и n линии после?

+0

Can модели существуют более чем в два раза в каждом файле? Вы хотите заменить только 2 экземпляра? – anubhava

+1

Он не имеет ничего общего с Perl, но с 'find': если вы используете _GNU find_, тогда вы можете написать ' find ./ -type f -exec perl ... '{}' + 'вместо' find ./ -type f -exec perl ... '{}' \; '. Обратите внимание на '+' вместо '\;'. 'find' будет вызывать' perl' с несколькими именами файлов одновременно (столько, сколько вписывается в командную строку) и, таким образом, значительно уменьшает общее время выполнения. – PerlDuck

+1

@PerlDog Спасибо. Это значительно улучшило его. – Nik

ответ

1

Это более грубая сила, чем элегантная, но я думаю, что это удалит линию с matchin g и строку, следующую за ней.

find ./ -type f -exec perl -i -e '$x=0 ; while (<>) {if ($_ =~ /<pattern>/) { $x++; next; }; if ($x) { $x=0; next; }; print "$_";}' {} \; 
+0

Спасибо! Я хочу удалить следующие 4 строки, поэтому как мне это сделать? Я полагаю, мне нужно изменить 'next' на что-то еще? – Nik

1

Возьмите файл:

aaa 
bbb 
ccc 
ddd 
eee 
fff 

Теперь мы хотим удалить из bbb в ccc, так:

perl -i -0pe 's/bbb.*ccc//ms' file 

0 будет хлебать файл по каждому пункту

+0

Спасибо за простое решение, но я ищу что-то, что будет работать сразу для нескольких файлов. – Nik

+1

Итак, добавьте этот 'perl' cmd в свою оригинальную находку, может быть?! –

+0

В обоих случаях удаляется только первая часть строки. Так что если это 's/aaabbbeee. * Eeecccfff // ms', он оставил бы' eee' и 'fff' и помещал их в одну строку. – Nik

0

Это ответ на perl только для одного файла. Я не хочу, чтобы кто-то, кто нашел этот вопрос, не понимает, что find, который вы его обернули, также будет редактировать скрытые файлы.

Ответ:

perl -ni -e '$ml=$. if /<pattern>/; print unless (defined $ml && $.<=$ml+[n])' input-file

Объяснение:

perl -ni будет читать и заменить input-file, но печатать только если указание

$ml=$. if /<pattern>/ устанавливает переменную $ml соответствующую строку в $., что текущая строка входного файла

print unless (defined $ml && $.<=$ml+[n]) будет печатать каждую строку, за исключением линии, которая соответствует и [п] следующие строки

+0

@Nik, чтобы ответить на ваш вопрос по другому ответу, решение для удаления строки и следующего 4: 'find ./ -type f -exec perl -ni -e '$ ml = $. если/ /; print (если не указано $ ml && $. <= $ ml + 4) '{} + ' – stevesliva