我想以这样的方式处理文件:从多行读取并创建一个新文件,该文件将有一行对应于此。
例如: 输入文件:
12345 1 - - -
12346 - 2 - 4
12347 - - 3 -
12348 5 - - -
12349 - 6 - 8
12350 - - 7 -
输出文件:
12346 1 2 3 4
12349 5 6 7 8
用3行代表完整的一行。
如何在perl中执行此操作?
答案 0 :(得分:2)
通过3个简单步骤完成:
创建一个哈希,将第一个单词保留为键。
从文件中读取并将输入保存在数组中。
针对每个键将元素打印到新文件。
答案 1 :(得分:1)
perl -lane'
$r = $. % 3;
$f = $F[0] if $r==2;
$arr[$_] += $F[$_] for 1 .. $#F;
if (!$r) { print "$f @arr"; @arr=() }
' file
输出
12346 1 2 3 4
12349 5 6 7 8
答案 2 :(得分:0)
这是我的解决方案。输入和输出文件是命令行的第1和第2个参数:
#!/usr/bin/perl
use warnings;
use strict;
open(DATA, "<", $ARGV[0]) or die $!;
open(OUTPUT, ">", $ARGV[1]) or die $!;
my $count = 0;
my $id = 0;
my @arr;
foreach (<DATA>){
chomp;
my @data;
# if line is not empty
if($_ ne ""){
@data = split(" ", $_);
$id = $data[0];
# merge data
for(my $i = 1; $i <= $#data; $i++){
if($data[$i] ne "-"){
$arr[$i] = $data[$i];
}
}
$count++;
if ($count == 2){
$arr[0] = $id;
} elsif ($count == 3){
# reset countable variable
$count = 0;
# print output
print OUTPUT join " ",@arr,"\n";
}
}
}
close(DATA);
close(OUTPUT);
答案 3 :(得分:0)
我认为这会对你有所帮助,如果有任何澄清让我知道:
输入文件是:
12345|1|-|-|-
12346|-|2|-|4
12347|-|-|3|-
12348|5|-|-|-
12349|-|6|-|8
12350|-|-|7|-
脚本
use strict;
use warnings;
sub processor{
(my @tmp )=@_;
my @inner;
shift(@tmp);
foreach my $element(@tmp){
$_=$element;
if((m/[0-9]/)){
push(@inner,$element);
}
}
return @inner;
}
open(INFILE,"infile.dat") or die "$!";
open(OFILE,">outfile.dat") or die "$!";
my @ecollector;
my $keyVal;
my $counter;
while(<INFILE>){
chomp($_);
my @tmp=split('\|',$_);
if(($. % 3) ne 0){
if(($. % 3) eq 2){ $keyVal=$tmp[0];}
push(@ecollector,processor(@tmp));
}
else{
push(@ecollector,processor(@tmp));
print OFILE "$keyVal\t".join("\t",sort(@ecollector))."\n";
@ecollector=();
}
}
close(INFILE);
close(OFILE);