MATLAB中上三角矩阵的一般导入

MATLAB中上三角矩阵的一般导入,matlab,matrix,Matlab,Matrix,我一直在尝试对我先前关于导入上三角矩阵的内容进行一般性导入 初始数据: 因此,您必须移动最后两行,如下所示: A(2,:) = circshift(A(2,:),[0 1]) A(3,:) = circshift(A(3,:),[0 2]) A = 1.0000 3.3200 -7.2300 NaN 1.0000 0.6000 NaN NaN 1.0000 然后用对称的NAN替换NAN: A(isnan(A)) =

我一直在尝试对我先前关于导入上三角矩阵的内容进行一般性导入

初始数据:

因此,您必须移动最后两行,如下所示:

A(2,:) = circshift(A(2,:),[0 1])
A(3,:) = circshift(A(3,:),[0 2])

A =

    1.0000    3.3200   -7.2300
    NaN       1.0000    0.6000
    NaN       NaN       1.0000
然后用对称的NAN替换NAN:

A(isnan(A)) = A(isnan(A)')

A =

    1.0000    3.3200   -7.2300
    3.3200    1.0000    0.6000
   -7.2300    0.6000    1.0000
我有这个,所以我们得到了任意大小的完整矩阵:

这是最好的方法吗?一定有更好的。我记得有人告诉我不要在MATLAB中使用for循环

更新 这就是结果。有没有什么方法可以让它在没有循环的情况下更快

A = importdata('A.txt')
for i =  (1:size(A)-1)
    A(i+1,:) = circshift(A(i+1,:),[0 i])
end
A(isnan(A)) = 0;
A = A + triu(A, 1)';

这里有一条没有回路的路。如果你有一个更新版本的Matlab,你可能想检查哪个解决方案真的更快,因为循环不像以前那么糟糕

A = A'; %'# transpose so that linear indices get the right order
out = tril(ones(size(A))); %# create an array of indices
out(out>0) = A(~isnan(A)); %# overwrite the indices with the right number
out = out + triu(out',1); %'# fix the upper half of the array

这是另一个通用的解决方案,适用于任何大小的上三角矩阵。它使用以下功能,并且:


看到我更新的答案,我认为这应该行得通。我有Matlab7.11.0 R2010b,所以你的解决方案更快,对吗?在较低版本的MATLAB中???@darkcminor:在旧版本的MATLAB中,我认为<2007,但我可能错了,做循环是非常昂贵的,因为MATLAB基本上一直在解释循环中的一切。在较新的版本中,情况已不再如此,因此性能增益可能较小或在较新的版本中不存在。循环仍然会导致大量函数调用,这是低效的。因此,在大多数情况下,对代码进行矢量化仍然是有意义的。@darkcminor:我认为即使使用较新版本的Matlab,我的解决方案也可能更快。请参阅@Egon的注释以获得极好的解释,尽管它需要更多的内存,因为您不能简单地覆盖A。@Ghaul:始终是一种乐趣:。顺便说一句,很好地访问了importdata。
A = importdata('A.txt')
for i =  (1:size(A)-1)
    A(i+1,:) = circshift(A(i+1,:),[0 i])
end
A(isnan(A)) = 0;
A = A + triu(A, 1)';
A = A'; %'# transpose so that linear indices get the right order
out = tril(ones(size(A))); %# create an array of indices
out(out>0) = A(~isnan(A)); %# overwrite the indices with the right number
out = out + triu(out',1); %'# fix the upper half of the array
>> A = [1 3.32 -7.23; 1 0.6 nan; 1 nan nan];  %# Sample matrix
>> A = spdiags(rot90(A),1-size(A,2):0);       %# Shift the rows
>> A = A+triu(A,1).'                         %'# Mirror around the main diagonal

A =

    1.0000    3.3200   -7.2300
    3.3200    1.0000    0.6000
   -7.2300    0.6000    1.0000