in reply to Parallel::ForkManager run_on_finish exit code handler

Use a closure:

my $stats = []; my $code = create_closure( $stats ); .... $pm->run_on_finish( $code ); .... print Dumper( $stats ); sub create_closure { my( $stats ) = @_; return sub { my ($pid, $exit_code, $ident) = @_; push( @$stats, { pid => $pid, exit_code => $exit_code, ident => $ident } ); } }

-derby

Replies are listed 'Best First'.
Re^2: Parallel::ForkManager run_on_finish exit code handler
by ikegami (Patriarch) on Sep 08, 2009 at 16:07 UTC
    He already is, which is why I asked to see the problem.

      Unless the OP edited the code, his example does not have a closure. He alluded to tracking the exit codes via a HASH but that sounded more like a global than a closure. I believe the OP may be looking for someway to update his database inside the run_on_finish command -- in that case he could just close over the database handle instead of some data structure which could be manipulated *after* the run of all the children.

      Update: ... forgot an (untested) example:

      my $dbh = create_dbh_handle(); my $code = create_closure( $dbh ); .... my $pm = Parallel::ForkManager->new( $MAX_NR_PROCESSES ); $pm->run_on_finish( $code ); foreach ... { my $pid = $pm->start and next; ... $pm->finish; # Terminates the child process } sub create_closure { my( $dbh ) = @_; return sub { my ($pid, $exit_code, $ident) = @_; my $sql = "insert into table values( $pid, $exit_code )"; $dbh->do( $sql ); } }

      -derby

        Unless the OP edited the code, his example does not have a closure.

        He didn't edit anything.

        sub { my ($pid, $exit_code, $ident) = @_; ... } is a closure that captures $MAX_PROCESSES, $pm, and anything else he declares there (like $stats or $dbh).

        You didn't create a closure, you just refactored the code. As such, your solution still doesn't work. See Re^3: Parallel::ForkManager run_on_finish exit code handler for a description of the actual problem and a solution for it.