If there are explicit examples in another post please let me know. I am having problems with interleaved printing from my threads. I am trying to control my threads by using a shared variable across all threads. The pseudo code below highlights the pieces of my code giving me problems. I have tried everything to make the threads wait their turns to print. Right now only a few output lines are being destroyed.
#!/usr/bin/perl
use threads;
use threads::shared;
my $PRINTFLAG :shared = 1;
Run_Threads();
sub Do_stuff{
lock($PRINTFLAG);
cond_wait($PRINTFLAG) until $PRINTFLAG == 1;
$PRINTFLAG = 0;
print "$working\n";
$PRINTFLAG =1;
}
Sub to spawn threads.
sub Run_Threads{
my @threads;
for (my $i = 1; $i <= 5; $i++){
push @threads, threads->create(\&Do_stuff);
}
foreach (@threads){
$_->join;
}
}
It would seem that each thread has its own handle, and thus its own output buffer. Considering that Perl file handles can't be shared using the mechanisms in threads::shared, that's not very surprising.
That means you need to flush the handle's buffer before releasing the lock. You can do that explicitly:
select->flush(); # Flush handle currently default for print.
Or you can have perl flush automatically after every print to that handle:
select->autoflush(1); # Autoflush handle currently default for print.
$| = 1; # Autoflush handle currently default for print.
Note: To use the ->flush and ->autoflush methods (but not for $|=1;) before Perl 5.14, you'll need to also load IO::Handle.
By the way,
my $PRINTFLAG :shared = 1;
lock($PRINTFLAG);
cond_wait($PRINTFLAG) until $PRINTFLAG == 1;
$PRINTFLAG = 0;
print "$d\n";
$PRINTFLAG =1;
can be simplified to
my $PRINTMUTEX :shared;
lock($PRINTMUTEX);
print "$d\n";
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With