2012-12-19 7 views
8

Ho bisogno di leggere da un file, scorrere attraverso di esso e scrivere la riga su un altro file. Quando il numero di linee raggiunge una soglia, chiudere l'handle del file di output e aprirne uno nuovo.In Perl, come evitare di aprire file più volte

Come evitare di aprire e chiudere l'handle del file di output ogni volta che si legge una riga dall'impugnazione del file di input come indicato di seguito?

use autodie qw(:all); 

my $tot  = 0; 
my $postfix = 'A'; 
my $threshold = 100; 

open my $fip, '<', 'input.txt'; 
LINE: while (my $line = <$fip>) { 
    my $tot += substr($line, 10, 5);  
    open my $fop, '>>', 'output_' . $postfix; 
    if ($tot < $threshold) { 
     print {$fop} $line; 
    } 
    else { 
     $tot = 0; 
     $postfix++; 
     redo LINE; 
    } 
    close $fop; 
} 
close $fip; 
+3

Non aprire e chiudere il file all'interno del ciclo for. Sposta il comando 'open' sopra il ciclo for. –

risposta

11

Riaprire il file solo quando si modifica $postfix. Inoltre, puoi essere un po 'più semplice.

use warnings; 
use strict; 
use autodie qw(:all); 

my $tot  = 0; 
my $postfix = 'A'; 
my $threshold = 100; 

open my $fop, '>>', 'output_' . $postfix; 
open my $fip, '<', 'input.txt'; 
while (my $line = <$fip>) { 
    $tot += substr($line, 10, 5);  

    if ($tot >= $threshold) { 
     $tot = 0; 
     $postfix++; 
     close $fop; 
     open $fop, '>>', 'output_' . $postfix; 
    } 
    print {$fop} $line; 
} 
close $fip; 
close $fop; 
+2

+1 ma penso che dovresti mantenere solo la seconda parte della risposta. –

+0

E puoi aggiungere in fondo: 'if (tell ($ fop)! = -1) {chiudi $ fop; } 'per chiuderlo. –

+4

Si dovrebbe sempre controllare l'errore quando si aprono i file. A meno che, naturalmente, tu non stia usando il modulo 'autodie'. Quale sei :) – TLP