1

我试图通过使用来加速我的 MATLAB 代码parfor,但是,我做错了。我的代码相当简单,我使用 MATLAB 的内置函数通过对均值 ( ) 和方差 ( )mle使用不同的初始猜测来拟合一些数据。是我的概率密度函数。mmvvonestagepdf2

这是代码片段:

mm=linspace(.1, 1, 2); % mean
vv=linspace(.1, 2, 2); % variance
N=length(mm);
n=length(vv);

pd=zeros(n*N,2);
ld = NaN*ones(n*N,1);

options = statset('MaxIter',10000, 'MaxFunEvals',10000);

parfor i=1:N  % pick a mean
    m=mm(i);
    parfor j=1:n  %  pick a variance
        v=vv(j);
        x0=[m,v];
        [p,conf1]=mle(data,'pdf',@onestagepdf2,'start',x0, 'upperbound', [Inf Inf],'lowerbound',[0 0],'options',options)
        pd(n*(i-1)+j,:)=p;  % store parameter values from mle
        l=onestagepdf2(data,p(1),p(2)); % evaluate pdf with parameter values
        ld(n*(i-1)+j)=sum(log(l));  % store likelihood value

    end
end

我收到的错误是:

“parfor 中的变量 pd 无法分类。”

4

2 回答 2

2
pd = zeros(n, N, 2); %initialise culprits
ld= zeros(n,N);
parfor ii=1:N  % pick a mean
    m=mm(ii);
    for jj=1:n  %  Parallellise the second parfor
        v=vv(jj);
        x0=[m,v];
        [p,conf1]=mle(data,'pdf',@onestagepdf2,'start',x0, 'upperbound', [Inf Inf],'lowerbound',[0 0],'options',options)
        pd(ii, jj, :) = p;=p;  % store parameter values from mle
        l=onestagepdf2(data,p(1),p(2)); % evaluate pdf with parameter values
        ld(ii,jj)=sum(log(l));  % store likelihood value

    end
end

pd正如@Trilarion 所说,您确实是您遇到错误的罪魁祸首。可能ld也不是太好,使用相同的语法,所以也初始化它。发生这种情况是因为想在执行之前parfor知道循环内所有变量的大小。MATLAB 不知道这是一个固定的最大大小,因为您正在使用循环变量来“更改”大小。

当您将其作为for循环运行时,您可能在这两行下方有“橙色摆动”(如拼写检查错误),说“pd 每次迭代的大小似乎都在增长。请考虑预先分配速度”。这是 所要求parfor,因为迭代的顺序不是连续的,因此不可能以这种方式增长数组。

其次,你不能嵌套parfor循环。您可以使用带有 a 的函数之类的东西parfor并在 中运行它parfor,但这不会让您加快速度,因为您已经在使用所有工作人员。

请参阅在 Matlab 中使用 parfor 节省时间和内存?了解更多parfor关于速度的一般信息。

于 2015-11-03T10:30:56.440 回答
1

您想要一个切片的输出变量,但 Matlab 不够聪明,无法检测到n*(i-1)+j它实际上是合理的,并且不会干扰异步评估。

只需将其作为单独的维度进行

pd = zeros(n, N, 2);
...
  % in the loop
  pd(i, j, :) = p;

那可行。

请注意,Matlab 不允许嵌套 parfors。N但是,如果大于工人的数量,您也不需要它们。另请参阅文档

于 2015-11-03T10:24:56.047 回答