2016-11-15 4 views
2

Ich versuche, eine Möglichkeit zu finden, eine Fortschrittsleiste in der Befehlszeile während der Analyse von Protokolldateien zu drucken. Erhalte Logfiles => foreach file => foreach line {do}.Drucken funktioniert nicht, während Iterationen in foreach Schleife gehen

Die Idee: Ich möchte in jeder "foreach file" -Schleife einen Teil der Fortschrittsanzeige drucken. Meaing: Drucken Sie den gesamten Balken, wenn Sie nur 1 Datei analysieren. Drucken Sie die Hälfte des Balkens für jede Datei, wenn Sie 2 Dateien usw. analysieren. Sie finden den spezifischen Code unten.

Das Problem: Die Ausgabe (print "*") wird gedruckt, nachdem ALLE foreach Iteration erfolgt sind - nicht dazwischen. Details sind im Code.

Hat jemand eine Idee, wie man innerhalb einer foreach druckt? Oder kann mir das Problem sagen? Ich verstehe es nicht :(.

my @logfiles=glob($logpath); 

print "<------------------>\n"; 
$vari=20/(scalar @logfiles); 

foreach my $logfile (@logfiles){ 
    open(LOGFILEhandle, $logfile); 
    @lines = <LOGFILEhandle>; 

    print "*" x $vari; #won't work, only after loop. Even a "print "*";" doesn't work 

    foreach my $line (@lines){ 
     #print "*"; works "in between". print "*" x $vari; does not. 

     if ($line=~/xyz/){ 
      ...... 
      ...... 
     } 
    close(LOGFILEhandle); 
    } 
} 
+1

Probieren Sie "print" * "x $ vari," \ n ";' oder setzen Sie $ | = 1. Vielleicht leiden Sie unter Pufferung (http://perl.plover.com/FAQs/Buffering.html). – PerlDuck

Antwort

3

Sie leiden an Pufferung. Der Ausgang gepuffert wird, bis eine bestimmte Menge erreicht ist oder Sie eine neue Zeile zu drucken. Um dieses Verhalten zu ändern, einfach

hinzufügen
$| = 1 ; 
..

am Anfang der Datei Dieses auf Autoflushing für STDOUT verwandeln es gibt mehr als einen Weg, um es und ein wenig länger und weniger kryptisch ist Borodins Vorschlag zu tun:

STDOUT->autoflush(); 
+2

'STDOUT-> autoflush' ist viel selbsterklärender und kann für jedes Dateihandle verwendet werden. – Borodin

+0

"Pufferung leiden" klingt wie ein häufiges Problem :). 5 Zeichen haben es funktioniert. Vielen Dank! – Ocalion

+0

@Borodin Ja, Sie haben Recht ... Ich habe Ihren Vorschlag der Antwort hinzugefügt. – dgw

3

Ich würde vorschlagen, Term::ProgressBar Modul zu vermeiden, das Rad neu zu erfinden.

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

use Term::ProgressBar; 

my @files = qw (file1 file2 file3 file4); 

my $progress = Term::ProgressBar->new(scalar @files); 

for ([email protected]) { 
    $| = 1; 
    sleep(1); #introducing sleep for demo purpose otherwise bar will fill up quickly 
    #open the file, do some operations and when you are done 
    #update the bar 
    $progress->update($_); 
} 
Verwandte Themen