繁体   English   中英

MATLAB - 稀疏到密集矩阵

[英]MATLAB - sparse to dense matrix

我在由代码(不是MATLAB )生成的数据文件中有一个稀疏矩阵。 数据文件由四列组成。 前两列是矩阵项的实部和虚部,第三列和第四列分别是对应的行和列索引。

我使用以下脚本在Matlab中将其转换为密集矩阵。

tic
dataA = load('sparse_LHS.dat');
toc
% Initialise matrix
tic
Nr = 15; Nz = 15; Neq = 5;
A (Nr*Nz*Neq,Nr*Nz*Neq) = 0;
toc

tic
lA = length(dataA)
rowA = dataA(:,3); colA = dataA(:,4);
toc

tic
for i = 1:lA
    A(rowA(i), colA(i)) = complex(dataA(i,1), dataA(i,2));
end
toc

然而,这个 scipt 非常慢( for循环是罪魁祸首)。

经过的时间是 0.599023 秒。

经过的时间是 0.001978 秒。

经过的时间是 0.000406 秒。

经过的时间是 275.462138 秒。

matlab有什么快速的方法可以做到这一点吗?

这是我到目前为止尝试过的:

parfor - 这给了我

有效索引在 parfor 循环中受到限制

我厌倦了将for循环重铸for这样的:

A(rowA(:),colA(:)) = complex(dataA(:,1), dataA(:,2));

我得到一个错误

下标分配尺寸不匹配。

您上次尝试不起作用的原因是 Matlab 无法获取列和行的下标列表,并将它们匹配以按顺序分配元素。 相反,它从列表中创建行和列的所有组合 - 这是它的外观:

dataA = magic(4)
dataA =
    16     2     3    13
     5    11    10     8
     9     7     6    12
     4    14    15     1

dataA([1,2],[1,4]) =

    16    13
     5     8

所以我们得到了 4 个元素 ( [1,1] , [1,4] , [2,1] , [2,4] ) 而不是 2 ( [1,1][2,4] )。

为了在列表中使用下标,您需要将它们转换为线性索引,一种简单的方法是使用函数sub2ind

使用此函数,您可以编写以下代码来一次性完成所有操作:

% Initialise matrix
Nr = 15; Nz = 15; Neq = 5;
A(Nr*Nz*Neq,Nr*Nz*Neq) = 0;
% Place all complex values from dataA(:,1:2) in to A by the subscripts in dataA(:,3:4):
A(sub2ind(size(A),dataA(:,3),dataA(:,4))) = complex(dataA(:,1), dataA(:,2));

sub2ind不是这么快的函数(但它会比你的循环快得多),所以如果你有很多数据,你可能想自己计算线性索引:

rowA = dataA(:,3);
colA = dataA(:,4);
% compute the linear index:
ind = (colA-1)*size(A,1)+rowA;
 % Place all complex values from dataA(:,1:2) in to A by the the index 'ind':
A(ind) = complex(dataA(:,1), dataA(:,2));

PS:

如果您使用的是 Matlab R2015b 或更高版本:

A = zeros(Nr*Nz*Neq,Nr*Nz*Neq);

比以下更快

A(Nr*Nz*Neq,Nr*Nz*Neq) = 0;

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM