Frage

Hallo ich habe ein einfaches Skript, das eine Datei nimmt und läuft einen weiteren Perl-Skript auf sich. Das Skript tut dies auf jede Bilddatei im aktuellen Ordner. Dies läuft auf einer Maschine mit zwei Quad-Core-Xeon-Prozessoren, 16 GB RAM, mit RedHat Linux.

Das erste Skript work.pl im Grunde ruft magicplate.pl einige Parameter übergibt und den Namen der Datei für magicplate.pl zu verarbeiten. Magie Platte dauert etwa eine Minute jedes Bild zu verarbeiten. Da work.pl wird die gleiche Funktion über 100 Mal Vorformen und weil das System über mehrere Prozessoren und Kerne ich über Splitting denken die Aufgabe, so dass es mehrfach parallel laufen können. Ich konnte die Bilder aufgeteilt in verschiedene Ordner, ggf. ergänzen. Jede Hilfe wäre toll. Danke

Hier ist, was ich habe, so weit:

use strict;
use warnings;


my @initialImages = <*>;

foreach my $file (@initialImages) {

    if($file =~ /.png/){
        print "processing $file...\n";
        my @tmp=split(/\./,$file);
        my $name="";
        for(my $i=0;$i<(@tmp-1);$i++) {
            if($name eq "") { $name = $tmp[$i]; } else { $name=$name.".".$tmp[$i];}
        }

        my $exten=$tmp[(@tmp-1)];
        my $orig=$name.".".$exten;

        system("perl magicPlate.pl -i ".$orig." -min 4 -max 160 -d 1");
     }
}       
War es hilfreich?

Lösung

Sie könnten Parallel verwenden :: ForkManager (set $ max_processes auf die Anzahl von Dateien gleichzeitig verarbeitet):

use Parallel::ForkManager;
use strict;
use warnings;

my @initialImages = <*>;

foreach my $file (@initialImages) {

    if($file =~ /.png/){
        print "processing $file...\n";
        my @tmp=split(/\./,$file);
        my $name="";
        for(my $i=0;$i<(@tmp-1);$i++) {
            if($name eq "") { $name = $tmp[$i]; } else { $name=$name.".".$tmp[$i];}
        }

        my $exten=$tmp[(@tmp-1)];
        my $orig=$name.".".$exten;

  $pm = new Parallel::ForkManager($MAX_PROCESSES);
    my $pid = $pm->start and next;
        system("perl magicPlate.pl -i ".$orig." -min 4 -max 160 -d 1");
    $pm->finish; # Terminates the child process

     }
}       

Aber wie von Hugmeir wieder Perl-Interpreter läuft und wieder für jede neue Datei ist keine gute Idee.

Andere Tipps

Sie sollten prüfen, nicht einen neuen Prozess für jede Datei zu erstellen, die Sie bearbeiten wollen - es ist schrecklich ineffizient und wahrscheinlich das, was die meiste Zeit hier stattfindet. Nur Perl laden und was auch immer Module, die Sie verwenden immer und immer sollte die Schaffung etwas Overhead sein. Ich erinnere mich an ein Plakat auf PerlMonks, der etwas tat ähnlich, und am Ende seiner zweiten Skript in ein Modul verwandeln, die Arbeitszeit- von einer Stunde auf ein paar Minuten reduziert . Nicht, dass Sie sollten erwarten, dass solch eine dramatische Verbesserung, aber man kann träumen ..

Mit dem zweiten Skript Refactoring als Modul, hier ist ein Beispiel für Thread Nutzung , in Welche BrowserUK erzeugt einen Thread-Pool, es Arbeitsplätze durch eine Warteschlange zugeführt wird.

  • Import "maigcplate" und die Verwendung Threading.
  • Start magicplate.pl im Hintergrund (Sie müßten Prozess Drosselung hinzufügen)
  • Import "magicplate" und Verwendung Gabel (Add Prozess Drosselung und ein kiddy Schnitter)
  • Erstellen „maigcplate“ ein Dämon mit einem Pool von Arbeitnehmern = Anzahl der CPUs
    • verwenden, um eine MQ-Implementierung für die Kommunikation
    • verwenden Sockets zur Kommunikation
  • Verwenden Sie Webserver (nginx, Apache, ...) und wickeln in REST für einen Webservice
  • etc ...

Alle diese drehen sich um mehrere Arbeiter zu schaffen, kann jeder Lauf auf ihren eigenen CPU. Bestimmte Implementierungen werden die Ressourcen besser nutzen (jene, die keinen neuen Prozess starten) und leichter zu implementieren und zu warten.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top