6

我不确定并行 for 循环的迭代独立意味着什么。以下是两个有效的并行 for 循环的示例吗?它们写入和读取相同的矩阵,但矩阵索引对于每次迭代都是唯一的。

X = zeros(64);
parfor i = 1:64^2
    X(i) = i;
end
parfor i = 1:64
    X(i,:) = X(i,:) .* randn(1,64);
end
4

1 回答 1

4

parfor目前而言,以下三种说法可以认为是等价的:

1)循环的迭代parfor必须是独立的。

2)循环的任何迭代都parfor可能取决于任何其他迭代的结果。

3)循环的迭代parfor必须能够以任何顺序执行(来自@Oli)

这些语句与常规循环相比如何?例如,在从 1 到 8 的典型循环中,第 4 次迭代可能取决于迭代 1、2 和 3,因为软件可以确定这些迭代在我们到达第 4 次迭代时已经发生。它不能取决于迭代 5、6、7 和 8,因为软件可以确定这些迭代不会发生。

正如@Oli 所说,在parfor循环中,循环可能以任何顺序发生。它们可能按以下顺序出现,例如,7 3 4 1 2 5 8 6。或者这 8 个数字的任何排列。这意味着一些非常重要的事情:没有办法知道哪个迭代将首先发生。要看到这一点,只需fprintf('Up to iteration %d of %d\n', t, T)在循环中插入一个,循环下标parfor在哪里,循环上限在哪里。tT

上面的陈述立即暗示了以下结论:由于任何迭代都可能首先发生,因此没有迭代取决于任何其他迭代的结果是至关重要的。我将用一些例子来结束答案:

X = ones(8, 8)
parfor n = 1:8
    X(:,n) = X(:,n) .* (3 * ones(8,1));
end

在这个例子中,(3 * ones(8,1))显然不依赖于任何其他迭代——相对于循环计数器是恒定的。同样X(:, n)不依赖于第 n 次以外的任何迭代。编辑:我之前randn在上面的示例中使用过 - 请参阅@AndrewJanke 提供的评论中的讨论,了解为什么这是一个坏主意。这种情况怎么办:

X = ones(8, 8);
parfor n = 1:8
    X(:,n) = X(:,n) + (n + 1);
end

这也是完全有效的。尽管n + 1表达式中有一个,但这与取决于迭代次数不同n + 1。相反,它只是将当前迭代次数的整数值加上 1 分配给X

最后,考虑:

X = ones(8, 1);
parfor n = 2:8
    X(n, 1) = X(n-1, 1) + 1;
end

这在常规循环中是完全有效的,因为迭代次数n-1总是在迭代之前出现n(假设我们正在向前循环)。但在parfor循环中,这将导致错误,因为迭代次数n可能发生在迭代次数之前n-1。Matlab 用来描述这里问题的术语称为“切片”。想象一下X被循环迭代分割。然后在第 n 次迭代中,您可能只会引用X.

最后一点,如果我对parfor循环有疑问,我阅读了文档中题为“Matlab 中的并行 for 循环 - 概述”的部分(抱歉,找不到相应的网页 - 对于 Matlab 文档来说不常见)它描述了所有循环内可能的变量分类,以及parfor循环对每个分类的限制。我在这个答案中讨论的实际上只是冰山一角。例如,诸如语句在循环n = n + 1中也是无效的parfor,因为n是循环变量,并且不允许对循环变量进行赋值。

于 2012-12-08T01:31:28.507 回答