为什么在while循环之后我只得到最后一行的值? [英] Why after the while loop I am only getting last row value?

查看:129
本文介绍了为什么在while循环之后我只得到最后一行的值?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

这是我正在读取的文件,

This is the files I am reading,

#Log1
Time    Src_id  Des_id  Address
0   34  56  x9870
2   36  58  x9872
4   38  60  x9874
6   40  62  x9876
8   42  64  x9878

#Log2
Time    Src_id  Des_id  Address
1   35  57  x9871
3   37  59  x9873
5   39  61  x9875
7   41  63  x9877
9   43  65  x9879

这是我写的代码,是我逐行读取然后拆分的代码

This the code I wrote where I am reading line by line and then spliting it

#!usr/bin/perl
use warnings;
use strict;

my $log1_file = "log1.log";
my $log2_file = "log2.log";

open(IN1, "<$log1_file" ) or die "Could not open file $log1_file: $!";
open(IN2, "<$log2_file" ) or die "Could not open file $log2_file: $!";

my $i_d1;
my $i_d2;
my @fields1;
my @fields2;
while (my $line = <IN1>) {
    @fields1 = split " ", $line;
   }
while (my $line = <IN2>) {
    @fields2 = split " ", $line;
   }
 
   print "@fields1\n";
   print "@fields2\n";
   

close IN1; 
close IN2;

我得到的输出

8 42 64 x9878
9 43 65 x9879

所需的输出

Time    Src_id  Des_id  Address
0   34  56  x9870
2   36  58  x9872
4   38  60  x9874
6   40  62  x9876
8   42  64  x9878
9 43 65 x9879
Time    Src_id  Des_id  Address
1   35  57  x9871
3   37  59  x9873
5   39  61  x9875
7   41  63  x9877
9   43  65  x9879

如果我使用 push(@ fields1,split" $ line); 我将得到这样的输出,

If I use push(@fields1 , split " ", $line); I am getting output like this,

Time Src_id Des_id Address 0 34 56 x9870 B 36 58 x9872 D 38 60 x9874 F 40 62 x9876 H 42 64 x9878

它应该打印整个数组,但只打印最后一行?同样在此之后,我需要比较两个"Times"(时间).日志&的一部分以顺序方式打印,但不知道如何在while循环中同时运行两个数组?请以没有任何模块的标准方式提出建议,因为我需要在其他服务器上运行它.

It should print whole array but printing just last row? Also after this I need to compare both the "Times" part of both log & print in sequence way but don't know how to run both array simultaneously in while loop? Please suggest in standard way without any modules because I need to run this in someone else server.

推荐答案

以下代码演示了如何读取和打印日志文件(OP并未指定他为何将行拆分为字段)

Following code demonstrates how to read and print log files (OP does not specify why he splits lines into fields)

use strict;
use warnings;
use feature 'say';

my $fname1  = 'log1.txt';
my $fname2  = 'log2.txt';
my $div     = "\t";

my $file1   = read_file($fname1);
my $file2   = read_file($fname2);

print_file($file1,$div);
print_file($file2,$div);

sub read_file {
    my $fname = shift;
    
    my @data;
    
    open my $fh, '<', $fname
        or die "Couldn't read $fname";
        
    while( <$fh> ) {
        chomp;
        next if /^#Log/;
        push @data, [split];
    }
        
    close $fh;
    
    return \@data;
}

sub print_file {
    my $data = shift;
    my $div  = shift;
    
    say join($div,@{$_}) for @{$data};
}

输出

Time    Src_id  Des_id  Address
0       34      56      x9870
2       36      58      x9872
4       38      60      x9874
6       40      62      x9876
8       42      64      x9878
Time    Src_id  Des_id  Address
1       35      57      x9871
3       37      59      x9873
5       39      61      x9875
7       41      63      x9877
9       43      65      x9879

让我们假设OP希望将两个文件合并为一个,并在 Time 字段上按行排序

Let's assume that OP wants to merge two files into one with sorted lines on Time field

  • Time 字段为键,将文件读入%data 哈希中
  • 打印标题( @fields )
  • 打印按 Time
  • 排序的哈希值
  • read files into %data hash with Time field as key
  • print header (@fields)
  • print hash values sorted on Time key
use strict;
use warnings;
use feature 'say';

my(@fields,%data);

my $fname1  = 'log1.txt';
my $fname2  = 'log2.txt';

read_data($fname1);
read_data($fname2);

say join("\t",@fields);
say join("\t",@{$data{$_}}) for sort { $a <=> $b } keys %data;

sub read_data {
    my $fname = shift;
    
    open my $fh, '<', $fname
        or die "Couldn't open $fname";
        
    while( <$fh> ) {
        next if /^#Log/;
        if( /^Time/ ) {
            @fields = split;
        } else {
            my @line = split;
            $data{$line[0]} = \@line;
        }
    }
        
    close $fh;
}

输出

Time    Src_id  Des_id  Address
0       34      56      x9870
1       35      57      x9871
2       36      58      x9872
3       37      59      x9873
4       38      60      x9874
5       39      61      x9875
6       40      62      x9876
7       41      63      x9877
8       42      64      x9878
9       43      65      x9879

这篇关于为什么在while循环之后我只得到最后一行的值?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆