Perl多线程-Perl退出并带有活动线程:已完成且未加入 [英] Perl Multithreading - Perl exited with active threads: finished and unjoined

查看:186
本文介绍了Perl多线程-Perl退出并带有活动线程:已完成且未加入的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试在程序中创建子例程的线程(称为重组).我使用下面的代码创建了线程,这些线程是我从 http:/改编而成的/chicken.genouest.org/perl/multi-threading-with-perl/我使用了此代码,因为这些线程是在循环中创建的,线程数取决于变量$ ParentTally,每个变量都不相同循环($ ParentTally最多可以达到1000,而我不想一次运行1000个线程)

I am trying to create threads of a subroutine in my program (called Recombination). I have used the code below to create the threads, which I adapted from http://chicken.genouest.org/perl/multi-threading-with-perl/ I used this code as these threads are created in a loop, with the number of threads dependent upon the variable $ParentTally which is different for each loop (and $ParentTally can be up to 1000, and I didn't want to run 1000 threads at once)

my $nb_process = 20;
my $nb_compute = $ParentTally;
my $i=0;
my @running = ();
my @Threads;
my %NewPopulation;

while (scalar @Threads < $nb_compute) {
    @running = threads->list(threads::running);
    if (scalar @running < $nb_process) {
        my $Offspring= threads->new (sub {Recombination(\%Parent1Chromosome, \%Parent2Chromosome)});
        push (@Threads, $Offspring);
        my $tid = $Offspring->tid;
    }

    @running = threads->list(threads::running);
    foreach my $thr (@Threads) {
        if ($thr->is_running()) {
           my $tid = $thr->tid;
        }
       elsif ($thr->is_joinable()) {
          my $tid = $thr->tid;
          my $Offspring1=$thr->join();
          $NewPopulation{$Offspring1}{'Tally'}+=1;
       }
    }
    @running = threads->list(threads::running);
    $i++;
}

while (scalar @running != 0) {
     foreach my $thr (@Threads) {
      if ($thr->is_joinable()){
         my $Offspring1=$thr->join(); 
         $NewPopulation{$Offspring1}{'Tally'}+=1;
      }
    }
    @running = threads->list(threads::running);
}

(注意:$ ParentTally取自代码前面的另一个哈希,即$ ParentTally = $ hashref-> {'Tally'};因此,程序的这一部分每次都以$ ParentTally的不同值循环. %Parent1染色体& %Parent2Chromosome在程序的前面创建. 子例程"Recombination"相当长,因此我没有发布它,但是它返回一个整数. )

(Note: $ParentTally is taken from another hash earlier in the code, my $ParentTally=$hashref->{'Tally'}; so this part of the program loops around with a different value for $ParentTally each time. %Parent1Chromosome & %Parent2Chromosome are created earlier in the program. The subroutine 'Recombination' is quite long so I haven't posted it, but it returns an integer. )

通常在运行程序时(尽管并非总是如此,许多早期代码依赖于随机变量,因此程序永远不会运行相同的变量)一旦完成,我会得到"Perl退出并带有活动线程:'number'已完成,并且未加入"(数字"取决于运行).我以为:

Often when running the program (although not always, a lot of the earlier code is dependent upon random variables so the program never runs the same) once it is finished I get 'Perl exited with active threads: 'number' finished and unjoined' ('number' varies depending upon the run). I thought that:

 while (scalar @running != 0) {
     foreach my $thr (@Threads) {
      if ($thr->is_joinable()){
         my $Offspring1=$thr->join(); 
         $NewPopulation{$Offspring1}{'Tally'}+=1;
      }
    }

是否意味着所有线程都会在进入下一部分代码之前完成?我究竟做错了什么? (我以前从未使用过线程).我曾考虑使用 http://www.perlmonks.org/?node_id=735931 ,但是我不太了解如何使用Thread :: Queue,也无法找到教程(也不了解 http://perldoc.perl.org/Thread/Queue.html ).谢谢

would mean all threads would finish before moving onto the next section of code? What am I doing wrong? (I have never used threads before). I had looked into using http://www.perlmonks.org/?node_id=735931 but I didn't really understand how to use Thread::Queue and wasn't able to find a tutorial (and didn't understand the http://perldoc.perl.org/Thread/Queue.html ). Thanks

推荐答案

我认为该错误位于最后一个while循环中:

I believe the error is in the last while loop:

while (scalar @running != 0) {
     foreach my $thr (@Threads) {
      if ($thr->is_joinable()){
         my $Offspring1=$thr->join(); 
         $NewPopulation{$Offspring1}{'Tally'}+=1;
      }
    }
    @running = threads->list(threads::running);
}

根据线程文档,对is_joinable的调用返回true仅当线程已完成运行,尚未分离且尚未加入时.我的猜测是,当您进入本节时,您仍然有正在运行的线程,因此可以跳过它们.您可以像在上一个while循环中一样,再次调用is_running,以查看是否仍有线程在运行并以某种方式处理线程.

According to the threads document, a call to is_joinable returns true only if a thread has finished running, hasn't been detached and hasn't been joined already. My guess is that when you get to this section you still have threads that are running, and so you skip over them. You might make another call, like you did in the previous while loop, to is_running to see if you still have threads running and handle the threads in some way.

这篇关于Perl多线程-Perl退出并带有活动线程:已完成且未加入的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆