我这样做:
sub worker {
my ($job, @action) = @$_; #<-- error thrown here
Build($job, @action[0]);
}
for (1..NUM_WORKERS) {
async {
while (defined(my $job = $q->dequeue())) {
worker($job);
}
};
}
$q->enqueue([$_, 'clean']) for @compsCopy;
# When you're done adding to the queue.
$q->end();
$_->join() for threads->list();
执行此操作时,我得到:
线程8异常终止:使用“严格引用”时,不能使用字符串(“8”)作为ARRAY引用(@上面引用的行)
我在这里做错了什么?
编辑:为了更深入地了解我想要实现的目标,我希望能够做到这样的事情:
$q->enqueue([$_, 'clean']) for @compsCopy; #clean
$q->enqueue([$_, 'l1']) for @compsCopy; #build
$q->enqueue([$_, '']) for @compsCopy; #link
用户可以指定何时运行脚本,哪些$action
他们想要对组件(目录)执行。
答案 0 :(得分:5)
如果worker的第一个参数是数组引用,则执行以下操作:
sub worker {
my ($job, @action) = @{$_[0]};
$_
和@_
可能看起来很相似,但它们是不同的变量。使用数组@_
来访问传递给该子例程的参数。 $_[0]
将保存该数组的第一个元素。
注意:我建议你为worker
子的第一个捕获参数提出一个不同的名称。重用$job
令人困惑。在子内部看起来my ($val, @action) = ...
可能在语义上更准确。
现在,如果我们撤消OP所做的所有更改,我们会返回使用saner参数顺序的内容,而不会使用名称$job
来执行两项不同的操作。
sub worker {
my ($job) = @_;
my ($job_type, @job_params) = @$job;
if ($job_type eq 'clean') {
clean(@job_params);
}
# elsif ($job_type eq '...') {
# ...
# }
# ...
}
for (1..NUM_WORKERS) {
async {
while (defined(my $job = $q->dequeue())) {
worker($job);
}
};
}
$q->enqueue([ clean => $_ ]) for @compsCopy;
# When you're done adding to the queue.
$q->end();
$_->join() for threads->list();