主要内容

使用GOP实现MPI_Allreduce功能

在这个例子中,我们看共和党函数及其构建的函数:gplusgcat.这些看似简单的函数实际上是并行编程中非常强大的工具。

共和党函数允许我们对在所有实验中定义的变量执行任何联合二进制操作。这使得我们不仅可以在所有实验室中对变量进行求和,还可以在所有实验室中找到变量的最小值和最大值,并将它们连接起来,然后执行许多其他有用的操作。

相关文档:

  • spmd在并行计算工具箱™用户指南中

在这个函数中可以找到这个例子中的代码:

函数paralleltutorial_gop

介绍

在进行并行编程时,我们经常会遇到这样的情况:在所有的实验室中都定义了一个变量,我们想要对这个变量进行操作,因为它在所有的实验室中都存在。例如,如果我们输入一个spmd语句并定义

spmdx = labindex;结束

在所有的实验室中,我们可能想要计算x在实验室。这就是gplus运算,它求和x在所有实验室中复制结果:

spmds = gplus (x)公关;结束

在spmd语句中分配的变量在客户机上表示为Composite。我们可以将实验室的结果值通过索引到Composite中,就像单元格数组一样:

年代{1}%显示实验1中s的值。所有的实验室都保存相同的价值。
ans = 78

同时,共和党,gplus,gcat允许我们指定函数输出应该返回到的单个实验室,它们会在其他实验室返回一个空向量。

spmdS = gplus(x, 1);结束年代{1}
ans = 78

这个示例展示了如何在所有实验室中执行与添加类似的一系列操作。在MPI中,这些操作被称为集合操作,如MPI_SUM、MPI_PROD、MPI_MIN、MPI_MAX等。

为示例创建输入数据

我们在所有示例中使用的数据非常简单:一个1乘2的变量数组,仅比x我们在开始时定义:

spmdX = labindex + (1:2)结束

使用GPLUS和GCAT

现在我们已经初始化了向量x对于实验室中不同的值,我们可以问这样的问题,例如,每个元素的值的和是多少x在实验室吗?那么乘积,最小值和最大值呢?正如我们的介绍所期望的那样,

spmds = gplus (x)公关;结束年代{1}
Ans = 90 102

的值逐个元素地返回x.然而,gplus只是……的特殊情况吗共和党operation, Global operation的缩写。的共和党函数允许我们跨实验室对变量数组的元素执行任何关联操作。关联运算最基本的例子是加法运算;它是关联的,因为加法独立于所使用的分组:

(a + b) + c = a + (b + c)

在MATLAB®中,加法可以用@plus函数句柄,所以我们也可以写gplus (x)公关作为

spmdS = gop(@plus, x);结束年代{1}
Ans = 90 102

我们可以连接这个向量x通过使用gcat函数,我们可以选择连接的维度。

spmdY1 = gcat(x, 1);沿行连接。Y2 = gcat(x, 2);%沿列连接。结束y1 y2 {1} {1}
ans = 2 3 3 4 5 4 5 6 6 7 7 8 9 9 8 10 10 11 11 12 12 13 13 14 ans = 1到13列2 3 3 4 4 5 6 5 6 7 7 8 8列14到24日9 9 10 10 11 11 12 12 13 13 14

GOP的其他基本用法

的值的元素与元素的乘积计算起来很简单x在实验室:

spmdP = gop(@times, x);结束p {1}
Ans = 1.0e+10 * 0.6227 4.3589

我们还可以逐元素求出的最大值x在实验室:

spmdM = gop(@max, x);M = gop(@min, x);结束M {1} {1}
Ans = 13 14 Ans = 2 3

逻辑运算

MATLAB甚至有更多内置的关联运算。属性表示逻辑与、或和异或操作@and,@or,@xor函数处理。例如,查看逻辑数组

spmdY = (x > 4)结束

然后,我们可以轻松地对元素执行这些逻辑操作y在实验室:

spmdYand = gop(@and, y);Yor = gop(@or, y);Yxor = gop(@xor, y);结束yand了{1}{1}yxor {1}
Ans = 1×2 logical array 0 0 Ans = 1×2 logical array 1 1 Ans = 1×2 logical array 1 0

按位操作

为了结束我们在MATLAB中构建的关联运算之旅,我们看一下按位的与、或和异或运算。这些是用@bitand,@bitor,@bitxor函数处理。

spmdXbitand = gop(@bitand, x);Xbitor = gop(@bitor, x);Xbitxor = gop(@bitxor, x);结束xbitand {1} xbitor {1} xbitxor {1}
Ans = 0 0 Ans = 15 15 Ans = 0 12

寻找最小和最大的位置

我们只需要做一点编程来找到对应于每个元素最大值的labindexx整个实验室都发生了。我们只需要几行代码就可以做到:

类型pctdemo_aux_gop_maxloc
function [val, loc] = pctdemo_aux_gop_maxloc(inval) % pctdemo_aux_gop_maxloc查找变量的最大值及其labindex。% [val, loc] = pctdemo_aux_gop_maxloc(inval)返回val在所有实验室中inval的最大值%。这个最大值%所在的labindex返回给loc。% Copyright 2007 The MathWorks, Inc. out = gop(@iMaxLoc, {inval, labindex*ones(size(inval))});val = {1};loc = {2};end function out = iMaxLoc(in1, in2) %计算最大值及其位置。将它们作为单元格数组返回。in1Largest = (in1{1} >= in2{1});maxVal = in1 {1}; maxVal(~in1Largest) = in2{1}(~in1Largest); maxLoc = in1{2}; maxLoc(~in1Largest) = in2{2}(~in1Largest); out = {maxVal, maxLoc}; end

当函数被实现时,它可以像任何内置操作一样简单地应用:

spmd[maxval, maxloc] = pctdemo_aux_gop_maxloc(x);结束maxloc [maxval {1}, {1})
Ans = 13 14 12 12

类似地,我们只需要几行代码就可以找到labindex,其中每个元素的最小值为x整个实验室发生了:

类型pctdemo_aux_gop_minloc
function [val, loc] = pctdemo_aux_gop_minloc(inval) % pctdemo_aux_gop_minloc查找变量最小值及其labindex。% [val, loc] = pctdemo_aux_gop_minloc(inval)返回val在所有实验中的最小值% inval。这个最小值%所在的labindex返回给loc。% Copyright 2007 The MathWorks, Inc. out = gop(@iMinLoc, {inval, labindex*ones(size(inval))});val = {1};loc = {2};end function out = iMinLoc(in1, in2) %计算最小值及其位置。将它们作为单元格数组返回。in1Smallest = (in1{1} < in2{1});minVal = in1 {1}; minVal(~in1Smallest) = in2{1}(~in1Smallest); minLoc = in1{2}; minLoc(~in1Smallest) = in2{2}(~in1Smallest); out = {minVal, minLoc}; end

我们可以很容易地找到最小值共和党

spmd[minval, minloc] = pctdemo_aux_gop_minloc(x);结束minloc [minval {1}, {1})
Ans = 2 3 1 1