在 MATLAB 循环期间加速巨大稀疏矩阵中的索引

Accelerating the index in huge sparse matrix during loop in MATLAB

我需要在迭代中构造一个巨大的稀疏矩阵。代码如下:

function Huge_Matrix = Create_Huge_Matrix(len, Weight, Index)

    k = size(Weight,1);

    Huge_Matrix = spalloc(len, len,floor(len*k));


    parfor i = 1:len
        temp = sparse(1,len);
        ind = Index(:,i);
        temp(ind) = Weight(:,i);
        Huge_Matrix(i,:) = temp;
    end


    Huge_Matrix = Huge_Matrix + spdiags(-k*ones(len,1),0,len,len);


end

如图所示,len是输入图片的高*重量的大小,对于200*200的图片,len是40000!我根据 Index 中存储的位置将 Weight 分配到这个巨大的矩阵中。即使我用parfor加速循环,速度也很慢

我一开始也尝试创建全矩阵,看起来代码可以变得更快,但内存有限。还有其他方法可以加快代码速度吗?提前致谢!

正如 在评论中所说,可能有比创建 40kx40k 矩阵更好的方法来完成您想要做的事情,但是如果您 要创建一个大的稀疏矩阵,最好让 MATLAB 帮你做。

sparse 函数有一个签名,它采用矩阵的非零元素的行、列和对应值的列表:

S = sparse(i,j,v) generates a sparse matrix S from the triplets i, j, and v such that S(i(k),j(k)) = v(k). The max(i)-by-max(j) output matrix has space allotted for length(v) nonzero elements. sparse adds together elements in v that have duplicate subscripts in i and j.

If the inputs i, j, and v are vectors or matrices, they must have the same number of elements. Alternatively, the argument v and/or one of the arguments i or j can be scalars.

所以,我们可以简单地传递 Index 作为行索引和 Weight 作为值,所以我们只需要一个与 Index 大小相同的列索引数组:

col_idx = repmat(1:len, k, 1);
Huge_Matrix = sparse(Index, col_idx, Weight, len, len);

(最后两个参数指定稀疏矩阵的大小。)

下一步是创建另一个大的稀疏矩阵并将其添加到第一个矩阵中。这似乎有点浪费,那么为什么不在创建矩阵之前将这些条目添加到现有数组中呢?

这是最终函数:

function Huge_Matrix = Create_Huge_Matrix(len, Weight, Index)

   k = size(Weight,1);
    
   % add diagonal indices/weights to arrays
   % this avoids creating second huge sparse array 
   Index(end+1, :) = [1:len];
   Weight(end+1, :) = -k*ones(1,len);
   
   % create array of column numbers corresponding to each Index
   % make k+1 rows because we've added the diagonal
   col_idx = repmat(1:len, k+1, 1);

   % let sparse do the work
   Huge_Matrix = sparse(Index, col_idx, Weight, len, len);

end