MATLAB - 通过垂直连接子矩阵重新排列矩阵

时间:2012-06-05 20:40:07

标签: matlab matrix

我遇到以下任务有问题: 假设一个3x6矩阵:

A =

0.2787    0.2948    0.4635    0.8388    0.0627    0.0435
0.6917    0.1185    0.3660    0.1867    0.2383    0.7577
0.6179    0.7425    0.0448    0.4009    0.9377    0.4821

我想做的是将矩阵划分为块,如下所示:

A =

0.2787    0.2948  |  0.4635    0.8388  |  0.0627    0.0435
0.6917    0.1185  |  0.3660    0.1867  |  0.2383    0.7577
0.6179    0.7425  |  0.0448    0.4009  |  0.9377    0.4821

并垂直连接这些块以获得最终结果:

0.2787    0.2948 
0.6917    0.1185  
0.6179    0.7425  
0.4635    0.8388
0.3660    0.1867
0.0448    0.4009
0.0627    0.0435
0.2383    0.7577
0.9377    0.4821

我想如果我能得到这方面的帮助,那么我也许可以 为任意矩阵做它A.我可以解决上述问题 使用for循环的问题,但我正在寻找一个矢量化解决方案。

提前致谢! Ñ

5 个答案:

答案 0 :(得分:3)

请考虑以下事项:

A = rand(3,6);
blkSz = 2;

C = mat2cell(A, size(A,1), blkSz*ones(1,size(A,2)/blkSz));
C = cat(1,C{:})

这假设size(A,2)可以被blkSz

整除

答案 1 :(得分:3)

这适用于您的矩阵为A且您想要的是D

C = mat2cell(A,[3],[2 2 2])
D = cat(1,C{:})

答案 2 :(得分:2)

可以这样做没有 cell2mat,(仅限reshapepermute),因此速度更快!

您需要使用"第三维"。它类似于描述的内容 split long 2D matrix into the third dimension

以下是上述矩阵的解决方案:

A1 = reshape(A, 3, 2, []);  % 3rd dimension is numel(A)/2/3
A2 = permute(A1, [2 1 3]);  % transpose 1st and 2nd dimension
Ans= reshape(A2, 2, [])' ;  % note the transpose

对于这种尺寸的矩阵,运行时间的差异可以忽略不计。但是,对于大矩阵,差异超过一个数量级:

A=rand(3, 2*10000);

%% good method

tic
A1 = reshape(A, 3, 2, []); %3rd dimension is numel(A)/2/3
A2 = permute(A1, [2 1 3]);
A3 = reshape(A2, 2, [])' ; %note the transpose'
toc

%% mat2cell method

tic
blkSz = 2;
C = mat2cell(A, size(A,1), blkSz*ones(1,size(A,2)/blkSz));
B3 = cat(1,C{:});
toc

%% make sure the answer is the same:
assert(max(A3(:)-B3(:))==0)

输出:

>> Elapsed time is 0.001202 seconds.
>> Elapsed time is 0.043115 seconds.

答案 3 :(得分:1)

这个怎么样:

width = 2; 
m = length(A(:))/width;
fn = @(i) reshape(A(:, i:width:end), m, 1);
B = cell2mat(arrayfun(fn, 1:width, 'UniformOutput', false));

只需在width变量中一次指定所需的列数。

答案 4 :(得分:0)

通过垂直连接,矩阵宽度可被3整除:

B = [ A(:,1:(size(A,2)/3)); A(:,size(A,2)/3+1:size(A,2)/3*2); A(:,size(A,2)/3*2+1:end) ];