主要内容

嵌套帕弗对于-Loops及其他帕弗要求

嵌套帕弗-Loops

你不能使用帕弗-在另一个循环中循环帕弗-循环。作为示例,以下是帕弗-不允许循环:

帕弗i=1:10帕弗j=1:5...终止终止

提示

你不能筑巢帕弗直接在另一个内部帕弗-循环。A.帕弗-loop可以调用包含一个函数帕弗-loop,但你没有得到任何额外的并行性。

MATLAB中的代码分析器®编辑标志使用帕弗在另一个里面帕弗-循环:

你不能筑巢帕弗-循环,因为并行化只能在一个级别上执行。因此,请选择要并行运行的循环,并将另一个循环转换为对于-环形。

在处理嵌套循环时考虑以下性能问题:

  • 并行处理开销招致。一般来说,你应该运行在平行的外循环,因为开销只发生一次。如果您并行运行的内循环,然后每一个多重的帕弗执行死刑会产生间接费用。看见将嵌套for循环转换为parfor循环例如,如何测量并行开销。

  • 确保迭代次数超过工作进程数。否则,您不会使用所有可用的工作进程。

  • 试着平衡这一点帕弗-loop迭代次数。帕弗试图补偿一些负载不平衡。

提示

始终并行运行最外层的循环,因为这样可以减少并行开销。

你也可以使用一个功能,用途帕弗并将其嵌入帕弗-环形。并行化仅在外水平发生。在以下示例中,调用一个函数我的乐趣里外帕弗-内环帕弗-loop嵌入我的乐趣按顺序运行,而不是并行运行。

帕弗i=1:10我的乐趣(i)终止作用MyFun(I)帕弗j=1:5...终止终止

提示

嵌套帕弗-loops一般没有给你计算的好处。

转换嵌套对于-Loops到帕弗-Loops

嵌套循环的典型用法是使用一个循环变量对一个维度进行索引,使用一个嵌套循环变量对另一个维度进行索引。基本形式是:

X=零(n,m);对于a=1:n对于b=1:mx(a,b)=乐趣(a,b)终止终止

下面的代码示出了简单的例子。用抽搐toc测量所需的计算时间。

A=100;抽搐对于i=1:100对于j=1:100a(i,j)=最大值(abs(eig(rand(a)));终止终止toc
运行时间为49.376732秒。

您可以并行化任何一个嵌套循环,但不能同时并行运行这两个循环。原因是并行池中的工作进程无法启动或访问其他并行池。

如果循环计数通过已转换为帕弗-loop,然后在池中的每个工作人员执行使用嵌套循环J循环计数器。这J循环本身不能作为循环运行帕弗每个工人。

因为并行处理会产生开销,所以必须仔细选择是要转换内部还是外部对于-loop到帕弗-环形。下面的示例示出了如何测量并行开销。

首先,仅转换外面的对于-loop到帕弗-循环。使用抽搐toc测量所需的计算时间。使用ticBytes总字节测量并行池中工作线程之间的数据传输量。

运行新代码,然后再次运行。第一次运行比后续运行慢,因为并行池需要一些时间来启动并使代码可供工作人员使用。

A=100;总字节(gcp);帕弗i=1:100对于j=1:100a(i,j)=最大值(abs(eig(rand(a)));终止终止tocBytes(GCP)TOC
BytesSentToWorkers BytesReceivedFromWorkers __________________ ________________________ 1 32984 24512 2 33784 25312 3 33784 25312 4 34584 26112总计1.3514e + 05 1.0125e + 05]经过时间是14.130674秒。

下一步仅转换从环到帕弗-与前一种情况一样,测量所需的时间和传输的数据。

A=100;总字节(gcp);对于i=1:100帕弗j=1:100a(i,j)=最大值(abs(eig(rand(a)));终止终止tocBytes(GCP)TOC
从工人处接收到的员工人数:1.3496e+06 5.487e+05 2 1.3496e+06 5.4858e+05 3 1.3677e+06 5.6034e+05 4 1.76E+06 5.47E+048E+048E总时间为638秒。

如果转换从环到帕弗-循环,传输的时间和数据量都比并行外循环大得多。在这种情况下,经过的时间几乎与嵌套对于-循环示例。加速比小于并行运行外部循环,因为您有更多的数据传输,因此有更多的并行开销。因此,如果您执行在并行循环中,与运行串行对于-环形。

如果希望减少并行开销并加快计算速度,请并行运行外部循环。

如果转换相反,外部循环的每次迭代都会启动一个单独的循环帕弗-环形。也就是说,内环转换创建100帕弗-循环。多个循环中的每个循环帕弗处决即被开销。如果你想减少并行开销,你应该并行运行,而不是外循环,因为开销只发生一次。

提示

如果您想加快代码的速度,请始终并行运行外部循环,因为这样可以减少并行开销。

嵌套对于-循环:要求和限制

如果要转换嵌套的对于-loop到帕弗-循环,必须确保循环变量已正确分类,请参阅parfor循环中的变量疑难解答.如果你的代码不符合标示为指导和限制必需的,您会得到一个错误。MATLAB在读取代码时捕捉到其中一些错误。这些错误被标记为必需(静态).

必需(静态):您必须定义对于-loop嵌套在一个帕弗-通过常量或广播变量进行循环。

在下面的示例中,左侧的代码不起作用,因为您定义了对于-通过函数调用进行循环。右边的代码提供了一种解决方法,首先在帕弗-循环:

无效的 有效的
A=零(100200);帕弗i=1:尺寸(A,1)对于j=1:尺寸(A,2)A(i,j)=i+j;终止终止
A=零(100200);n=尺寸(A,2);帕弗i=1:尺寸(A,1)对于j=1:na(i,j)=i+j;终止终止
必需(静态):嵌套对象的索引变量对于-循环只能由其自身进行显式赋值对于陈述。

必须遵守此限制。如果嵌套对于-循环变量在循环中的任意位置更改帕弗-循环而不是通过其对于语句所索引的区域对于-loop变量不保证可于每个工人。

左侧的代码无效,因为它试图修改嵌套的对于-loop变量J在循环体中。右侧的代码通过指定嵌套的对于-loop变量临时变量T,然后更新T.

无效的 有效的
A =零(10);帕弗i=1:10对于j=1:10a(i,j)=1;j=j+1;终止终止
A =零(10);帕弗i=1:10对于j=1:10a(i,j)=1;t=j;t=t+1;终止终止
必需(静态):您不能为嵌套的对于-循环变量。

必须遵守此限制。如果一个嵌套的对于-循环变量被索引,迭代不保证是独立的。

左侧的示例无效,因为它试图为嵌套的对于-loop变量J。右侧的示例将删除此索引。

无效的 有效的
A =零(10);帕弗i=1:10对于j=1:10j(1);终止终止
A =零(10);帕弗i=1:10对于J = 1:10焦耳;终止终止
必需(静态):在使用嵌套对于-循环变量对于索引切片数组,必须以普通形式使用该变量,而不是作为表达式的一部分。

例如,左侧的以下代码不起作用,但右侧的代码起作用:

无效的 有效的
A =零(4,11);帕弗i=1:4对于j=1:10a(i,j+1)=i+j;终止终止
A =零(4,11);帕弗i=1:4对于j=2:11a(i,j)=i+j-1;终止终止
必需(静态):如果您使用嵌套对于-循环以索引到切片数组中,不能在帕弗-环形。

在下面的例子中,左侧的代码不起作用,因为A.在嵌套的对于-循环。右边的代码可以工作,因为v分配给A.嵌套循环的外部:

无效的 有效的
A =零(4,10);帕弗i=1:4对于j=1:10a(i,j)=i+j;终止DISP(A(I,J))终止
A =零(4,10);帕弗I = 1:4 V =零(1,10);对于j=1:10V(j)=i+j;终止disp(v(j))A(i,:)=v;终止

帕弗-循环限制

嵌套的函数

尸体帕弗-循环无法引用嵌套函数。但是,它可以通过函数句柄调用嵌套函数。请尝试以下示例。请注意A(idx)=nfcn(idx)在里面帕弗-循环不起作用。你必须使用feval调用FCN处理帕弗-环体。

作用A=pfeg作用OUT = nfcn(上)出来= 1 +中;终止FCN = @nfcn;帕弗IDX = 1:10 A(IDX)= feval(FCN,IDX);终止终止
>>pfeg正在使用“本地”配置文件启动并行池(parpool)。。。连接到4名工人。ans=2 3 4 6 7 8 9 10 11

提示

如果使用的函数句柄引用帕弗-loop,那么外部范围变量的值不会工人之间是同步的。

嵌套帕弗-Loops

尸体帕弗-loop不能包含帕弗-循环。有关详细信息,请参阅嵌套parfor循环.

嵌套spmd声明

尸体帕弗-循环不能包含spmd声明,以及spmd语句不能包含帕弗-原因是工人无法启动或访问更多的并行池。

打破回来声明

尸体帕弗-循环不能包含打破回来考虑。帕菲尔帕菲瓦诺酒店相反,因为您可以使用取消在他们身上。

全球性和持久性变量

尸体帕弗-循环不能包含全球的持久的变量声明。原因是这些变量在worker之间不同步。你可以用全球的持久的函数中的变量,但它们的值仅对创建它们的工作人员可见。而不是全球的变量,使用函数参数共享值是更好的做法。

要了解有关可变需求的更多信息,请参阅parfor循环中的变量疑难解答.

脚本

如果脚本引入了一个变量,你不能从内调用此脚本帕弗-loop或spmd陈述原因是此脚本将导致透明度冲突。有关详细信息,请参阅确保parfor循环或spmd语句的透明度.

匿名函数

可以在函数体中定义匿名函数帕弗-循环。但是,不支持匿名函数中的切片输出变量。可以通过为切片变量使用临时变量来解决此问题,如下例所示。金宝app

x=1:10;帕弗i=1:10温度=x(i);匿名函数=@()2*temp;x(i)=匿名函数()+i;终止DISP(X);

有关切片变量的详细信息,请参见切片变量.

输入名称功能

使用输入名称返回对应于参数号工作区变量名不支持内部金宝app帕弗-循环。原因是帕弗工作人员无权访问MATLAB桌面的工作区。要解决此问题,请致电输入名称帕弗,如以下示例所示。

a=“a”;myFunction的(a)中作用X = myFunction的(a)中名称= inputname(1);帕弗i=1:2x(i)。(名称)=i;终止终止

负载功能

的语法负载内部不支持未分配给输出结构的金宝app帕弗-圈,里面帕弗,始终分配负载一个结构。

nargin纳古特功能

内部不支持以下用途金宝app帕弗-循环:

  • 使用nargin纳古特没有函数参数

  • 使用纳金奇克nargoutchk验证当前正在执行的函数调用中输入或输出参数的数量

其原因是工人没有访问MATLAB桌面工作空间。为了解决这个问题,调用这些函数之前,帕弗,如以下示例所示。

我的功能(“a”,“b”)作用X=myFunction(a,b)nin=nargin;帕弗i=1:2x(i)=i*nin;终止终止

P-代码脚本

您可以从中调用P代码脚本文件帕弗-循环,但P代码脚本不能包含帕弗-环形。要解决此问题,使用P码的功能,而不是一个P-代码的脚本。

另见

||

相关话题