我想在匹配图案或线条后打印特定数据。我有这样一个文件:
#******************************
List : car
Design: S
Date: Sun 10:10
#******************************
b-black
g-green
r-red
Car Type No. color
#-------------------------------------------
N17 bg099 g
#-------------------------------------------
Total 1 car
#******************************
List : car
Design: L
Date: Sun 10:20
#******************************
b-black
g-green
r-red
Car Type No. color
#-------------------------------------------
A57 ft2233 b
#-------------------------------------------
Total 1 car
#******************************
List : car
Design: M
Date: Sun 12:10
#******************************
b-black
g-green
r-red
Car Type No. color
#-------------------------------------------
L45 nh669 g
#-------------------------------------------
Total 1 car
#. .
#. .
#.
#.
我想打印数据,例如在“Type ....”行后面,并用“------”作为N17和bg099。我试过这个,但它无法正常工作。
my @array;
While (@array = <FILE>) {
foreach my $line (@array) {
if ($line =~ m/(Car)((.*))/) {
my $a = $array[$i+2];
push (@array, $a);
}
if ($array[$i+2] =~ m/(.*)\s+(.*)\s+(.*)/) {
my $car_type = "$1";
print "$car_type\n";
}
}
}
预期产出:
Car Type No.
N17 bg099
A57 ft2233
L45 nh669
.. ..
. .
答案 0 :(得分:6)
while (<FILE>) { #read line by line
if ($_ =~ /^Car/) { #if the line starts with 'Car'
<FILE> or die "Bad car file format"; #read the first line after a Car line, which is '---', in order to get to the next line
my $model = <FILE>; #assign the second line after Car to $model, this is the line we're interested in.
$model =~ /^([^\s]+)\s+([^\s]+)/; #no need for if, assuming correct file format #capture the first two words. You can replace [^\s] with \w, but I prefer the first option.
print "$1 $2\n";
}
}
或者如果您更喜欢更紧凑的解决方案:
while (<FILE>) {
if ($_ =~ /^Car/) {
<FILE> or die "Bad car file format";
print join(" ",(<FILE> =~ /(\w+)\s+(\w+)/))."\n";
}
}
答案 1 :(得分:4)
这是另一种选择:
use strict;
use warnings;
print "Car Type\tNo.\n";
while (<>) {
if (/#-{32}/) {
print "$1\t$2\n" if <> =~ /(\S+)\s+(\S+)/;
<>;
}
}
输出:
Car Type No.
N17 bg099
A57 ft2233
L45 nh669
用法:perl script.pl inFile [>outFile]
修改:简化
答案 2 :(得分:2)
我让你的代码可以进行一些小调整。 它仍然不完美但它有效。
代码:
$file_to_get = "input_file.txt";
open (FILE, $file_to_get) or die $!;
my @array;
while (@array = <FILE>) {
$i = 0;
foreach my $line (@array) {
if ($line =~ m/(Car)((.*))/) {
my $a = $array[$i+2];
push (@array, $a);
print $a;
}
$i++;
}
}
close(FILE);
答案 3 :(得分:2)
这样的事情:
while (my $line = <>) {
next unless $line =~ /Car\s+Type/;
next unless $line = <> and $line =~ /^#----/;
next unless $line = <>;
my @fields = split ' ', $line;
print "@fields[0,1]\n";
}
答案 4 :(得分:1)
perl -lne 'if(/Type/){$a=<>;$a=<>;$a=~m/^([^\s]*)\s*([^\s]*)\s/g; print $1." ".$2}' your_file
测试:
> perl -lne 'if(/Type/){$a=<>;$a=<>;$a=~m/^([^\s]*)\s*([^\s]*)\s/g; print $1." ".$2}' temp
N17 bg099
A57 ft2233
L45 nh669
如果你想使用awk,你可以这样做:
> awk '/Type/{getline;if($0~/^#---*/){getline;print $1,$2}}' your_file
N17 bg099
A57 ft2233
L45 nh669
答案 5 :(得分:1)
shell 单行做同样的事情
echo "Car Type No. "; \
grep -A 2 Type data.txt \
| grep -v -E '(Type|-)' \
| grep -o -E '(\w+ *\w+)'
答案 6 :(得分:1)
使用Perl触发器操作符的解决方案。从输入中假设您总是在感兴趣的块末尾有总线
cat $your_file | perl -ne '$a=/^#--/;$b=/^Total/;print if(($a .. $b) && !$a && !$b);'