I need to search for a pattern and write that line as well as the next 3 lines into a file (FILE). Is this a correct way to do it? Thanks.
print FILE if /^abc/;
$n=3 if /^abc/;
print FILE if ($n-- > 0);
I need to search for a pattern and write that line as well as the next 3 lines into a file (FILE). Is this a correct way to do it? Thanks.
print FILE if /^abc/;
$n=3 if /^abc/;
print FILE if ($n-- > 0);
You could simplify it to using a flag variable to know if you should print a line:
while( <$input> ) {
$n=4 if /^abc/;
print FILE if ($n-- > 0);
}
Besides simplification, it also fixes a problem: in your version the abc string will be printed twice.
I'd rather take a few extra lines of code and make everything more clear. Something like this should work:
my $count = 0;
while ( my $line = pop @file ) {
if ( /^abc/ ) {
$count = 4;
}
if ( $count > 0 ) {
print FILE $line;
$count--;
}
}
Edit to respond to comments:
There is no need to slurp the file in or try to write your code on a single line:
#!/usr/bin/perl
use strict;
use warnings;
while ( my $line = <DATA> ) {
if ( $line =~ /^abc/ ) {
print $line;
print scalar <DATA> for 1 .. 3;
}
}
__DATA__
x
y
z
abc
1
2
3
4
5
6
This is a feature of the command-line grep(1). No programming needed:
grep abc --after-context=3
You do get '--' lines between groups of context, but those are easy enough to strip. It's also easy enough to do the whole thing in Perl. :)
The trick is what you want to do when one of the following three lines also contains the pattern you're looking for. grep(1) will reset the counter and keep printing lines.
I like ..
operator:
perl -ne 'print if (/abc/ and $n=3) .. not $n--'
but you doesn't have described what should happen if abc pattern is repeated in following three lines. If you want restart counter, your approach is correct if fix a little bug with double print.
perl -ne'$n=4 if/abc/;print if$n-->0'
Another possible solution...
#!/usr/bin/perl
use strict;
my $count = 0;
while (<DATA>) {
$count = 1 if /abc/;
if ($count >= 1 and $count <= 3) {
next if /abc/;
print;
$count++;
}
}
__DATA__
test
alpha
abc
1
234123
new_Data
test