我有一个程序(Perl)启动了大量的线程(每个线程负责根据数据处理创建图形)。 我开始使用的每个线程:
my @threads //list to store threads that have been launched
push @threads,threads->create(\mySubName,params...);
线程正确启动但过了一会儿,在我打开其中几个Perl解释器崩溃后(我认为它与内存有关?)。所以我的解决方案是限制我一次打开的线程数,我选择了15.我想在每个创建行之前添加一个sub来检查是否可以在我等待时触发下一个线程或执行睡眠一个完成。这就是我尝试这样做的方式。
sub checkThreads{
my $addThread = 0;
until($addThread){
my $totalThreads = 0;
foreach my $task (@threads){
if($task->is_running()){$totalThreads++;}
}
if($totalThreads <= 15 ){
print "Ok to add new thread, carry on!\n";
$addthread = 1;
}else{
print "Waiting for $totalThreads threads to fire next one...\n";
sleep 2;
}
}
}
所以每次我想创建一个新线程时我都会调用
&checkThreads;
当我等待一些线程清理时,这会产生延迟。 问题是,当我打电话给那个子时,我点击我检查的那一刻:
$task->is_running()
程序退出并停止运行,没有任何错误或警告。我只想要一个计算正在运行的线程来限制它们的子。
如何成功执行此计数?
我尝试过的其他事情是评估以下内容:
scalar(threads->list());
但是这给了我一个奇怪的价值,就像它是一个不起眼的参考我相信看起来像:
threads=SCALAR(0x80fea8c)
答案 0 :(得分:6)
Thread::Semaphore提供counting semaphore来限制并发:
my $sem = Thread::Semaphore->new(15); # max 15 threads
my @threads = map {
# request a thread slot, waiting if none are available:
$sem->down;
threads->create(\&mySubName, @params)
} 0..100;
$_->join for @threads;
在你的功能中:
sub mySubName {
do_stuff();
# release slot:
$sem->up;
}
答案 1 :(得分:1)
查看文档,
my $count = threads->list();
应该有效,与你所说的相反。您使用的线程版本的文档说什么?好吧,您可以使用以下方法作为解决方法。
my $count = () = threads->list();
答案 2 :(得分:0)
man perlthrtut
What Threads Are Running?
"threads->list()" returns a list of thread objects, one for each thread
that's currently running and not detached. Handy for a number of
换句话说,找出列表中有多少项,其中threads-&gt; list()返回并且您有计数。
您可能需要调查Thread::Pool或其他cpan软件包,看看其他人是否已经为您完成了繁重的工作。