in reply to Read and analyze two file in parallel

remluvr:

Assuming the data is in the same order, it should be as easy as something like this (untested):

use strict; use warnings; use autodie; open my $IF1, '<', 'File.in1'; open my $IF2, '<', 'File.in2'; open my $OF, '>', 'File.out'; while (1) { my @Rec1 = split /\s+/, <$IF1>; my @Rec2 = split /\s+/, <$IF2>; $Rec1[-1] += $Rec2[-1]; print $OF join("\t", @Rec1), "\n"; last if eof($IF1) and eof($IF2); }

Of course, you'll have to add checking to verify that the records are compatible. If you sort the files beforehand, then in the event of a mismatch, you should be able to simply re-read the file containing the "smaller" (in value) string.

Update: As CountZero mentions, stopping the loop might be a good idea. So I added the last statement.

...roboticus

When your only tool is a hammer, all problems look like your thumb.

Replies are listed 'Best First'.
Re^2: Read and analyze two file in parallel
by CountZero (Bishop) on Mar 14, 2012 at 22:45 UTC
    Interesting, but how do you break from your while(1) loop?

    CountZero

    A program should be light and agile, its subroutines connected like a string of pearls. The spirit and intent of the program should be retained throughout. There should be neither too little or too much, neither needless loops nor useless variables, neither lack of structure nor overwhelming rigidity." - The Tao of Programming, 4.1 - Geoffrey James

    My blog: Imperial Deltronics
Re^2: Read and analyze two file in parallel
by remluvr (Sexton) on Mar 14, 2012 at 22:06 UTC

    Thanks! In the meanwhile I tried something and it worked, I post it here in case it could be helpful to someone (or in case you have suggestions to give me on it). Here it is:

    sub read_file_line { my $fh = shift; if ($fh and my $line = <$fh>) { chomp $line; return [ split(/\t/, $line) ]; } return; } #sub compute { # do something with the 2 values #} open(my $f1, $input); open(my $f2, $input_1); my $pair1 = read_file_line($f1); my $pair2 = read_file_line($f2); my $value; open OUT,">$file"; while ($pair1 and $pair2) { $value=$pair1->[3]*(1-$pair2->[3]); $pair1 = read_file_line($f1); $pair2 = read_file_line($f2); print OUT $pair1->[0]."\t".$pair1->[1]."\t".$pair1->[2]."\t".$valu +e."\n"; } close($f1); close($f2); close OUT;

    Thanks,
    Giulia

      Some suggestions:
      That's a bit awkward, because you call read_file_line() inside and outside your while loop, so maintenance-wise it would be easy to change one and forget to change the other. You could combine both calls into your while loop condition:

      while(my $pair1 = read_file_line($f1) and my $pair2 = read_file_line($ +f2)){

      Also, since you only use $value inside the loop, there's no need to declare it outside. Just declare it with my when you assign to it inside the loop. Declaring it outside the loop means it'll retain its value between loops, which shouldn't hurt in this case, but can make odd things happen if the assignment to it is ever conditional.

      In your print statement, there's no need to concatenate all those things. Just put your variables and \t characters inside one set of quotes.

      Aaron B.
      My Woefully Neglected Blog, where I occasionally mention Perl.

Re^2: Read and analyze two file in parallel
by Anonymous Monk on Mar 15, 2012 at 08:39 UTC

    Update: As CountZero mentions, stopping the loop might be a good idea. So I added the last statement.

    while(not( grep eof, $in1, $in2 )){
    ...
    }
      Correction grep \&eof, otherwise you're testing @ARGV