matlab 矩阵 三维矩阵相乘,将三维矩阵与二维矩阵相乘

我正在处理完全相同的问题,并着眼于最有效的方法。我看到的方法大致有三种,除了使用外部库(即,

mtimesx

):

循环通过三维矩阵的切片

重复和排列巫术

Cellfun乘法

我最近比较了这三种方法,看哪种方法最快。我的直觉是(2)会是赢家。代码如下:

% generate data

A = 20;

B = 30;

C = 40;

D = 50;

X = rand(A,B,C);

Y = rand(B,D);

% ------ Approach 1: Loop (via @Zaid)

tic

Z1 = zeros(A,D,C);

for m = 1:C

Z1(:,:,m) = X(:,:,m)*Y;

end

toc

% ------ Approach 2: Reshape+Permute (via @Amro)

tic

Z2 = reshape(reshape(permute(X, [2 1 3]), [A B*C]), [B A*C])' * Y;

Z2 = permute(reshape(Z2',[D A C]),[2 1 3]);

toc

% ------ Approach 3: cellfun (via @gnovice)

tic

Z3 = cellfun(@(x) x*Y,num2cell(X,[1 2]),'UniformOutput',false);

Z3 = cat(3,Z3{:});

toc

所有三种方法产生相同的输出(phew!)但是,令人惊讶的是,这个循环是最快的:

Elapsed time is 0.000418 seconds.

Elapsed time is 0.000887 seconds.

Elapsed time is 0.001841 seconds.

请注意,从一个试验到另一个试验的时间变化很大,有时(2)是最慢的。随着数据的增加,这些差异变得更加显著。但与

许多的

更大的数据,(3)比(2)。循环方法仍然是最好的。

% pretty big data...

A = 200;

B = 300;

C = 400;

D = 500;

Elapsed time is 0.373831 seconds.

Elapsed time is 0.638041 seconds.

Elapsed time is 0.724581 seconds.

% even bigger....

A = 200;

B = 200;

C = 400;

D = 5000;

Elapsed time is 4.314076 seconds.

Elapsed time is 11.553289 seconds.

Elapsed time is 5.233725 seconds.

但是循环法

可以

如果环尺寸比其他尺寸大得多,则应慢于(2)。

A = 2;

B = 3;

C = 400000;

D = 5;

Elapsed time is 0.780933 seconds.

Elapsed time is 0.073189 seconds.

Elapsed time is 2.590697 seconds.

所以(2)以一个大因素获胜,在这个(可能是极端的)情况下。可能并不是所有情况下都是最佳的方法,但是循环仍然很好,在许多情况下也是最佳的。在可读性方面也是最好的。走开!

你可能感兴趣的:(matlab,矩阵,三维矩阵相乘)