如何在 matlab 中矢量化以下循环?

How can I vectorize the following loops in matlab?

我正在使用 R2019a matlab。 我有一个矩阵,我想根据对 2 个附加向量所做的计算在某些位置填充值。 目前我正在用 2 个循环来做,但这并没有利用 matlab 的矢量化能力。

如何以矢量化方式执行以下脚本:

C = zeros(size(vecB), size(vecA));

% Calculate face-vertix connectivity of face area values:
posMat = sparse(A, repmat((1:size(A,1))',1,3), ...
                1, size(B,1), size(A,1));

for i = 1:size(B,1)
    for j = 1:size(A,1)
        if posMat(i,j) == 1
            C(i,j) = vecA(j)/vecB(i)/3;
        end
    end
end

脚本中变量的大小:

size(A)  =         5120           3
size(B)  =         2562           3
size(B)  =         2562        5120
size(posMat)  =    2562        5120
size(vecA) =       5120           1
size(vecB) =       2562           1

因为只有 posMat 的非零元素才能满足循环内的条件,所以提高效率的重要一点是利用向量化实现中的矩阵 sparse 这一事实。

如果您使用 sparse 条件的乘法作为将不符合条件的元素设置为 0 的方法(而不是使用 zeros 初始化矩阵),则只有通过条件的元素将被实际评估。

从 R2016b 开始,vecA.'./vecB/3implicitly expanded 到 return vecA(j)/vecB(i)/3 的完整 2562×5120 double array for all ij 的值。但是 (posMat == 1) .* vecA.'./vecB/3 return 是一个 2562×5120 sparse double array ,其中只对 posMat == 1.

的元素进行了除法计算

如果 Csparse 值可以接受,则

C = (posMat == 1) .* vecA.'./vecB/3;

就够了。如果需要完整存储形式,则可以简单地将此输出传递给 full 函数。