I'm trying to multiply every element in a small matrix (let's say 2x2) with every position in a big matrix (let's say 4x4), element by element.
So I want:
1 2 3 4 1 0 3 0
1 0 1 2 3 4 0 0 0 0
0 0 'x' 1 2 3 4 = 1 0 3 0
1 2 3 4 0 0 0 0
The small matrix is applied as many times as it fits, and the multiplication is element by element. I've tried a bunch of loops, but that doesn't feel right in MATLAB, there must be prettier ways of doing it?
One possibility is to use repmat
to repeat the small matrix as many times as necessary:
C = repmat(A,size(B,1)/size(A,1),size(B,2)/size(A,2)).*B
Another possibility, which avoids repmat
: cut up the large matrix, arrange the pieces in the third and fourth dimensions, and use bsxfun
to do the multiplication:
[m n] = size(A);
[M N] = size(B);
T = permute(reshape(B,M,n,[]), [2 1 3]);
T = permute(reshape(T,n,m,[],size(T,3)),[2 1 3 4]);
C = cell2mat(squeeze(mat2cell(bsxfun(@times,T,A),m,n,ones(1,M/m),ones(1,N/n))));
(The two lines T = ...
do the cutting, and are due to A. Donda.)
The advantage of this approach is that, if memory is an issue, you can overwrite B
instead of defining T
, thus saving memory:
[m n] = size(A);
[M N] = size(B);
B = permute(reshape(B,M,n,[]),[2 1 3]);
B = permute(reshape(B,n,m,[],size(B,3)),[2 1 3 4]);
C = cell2mat(squeeze(mat2cell(bsxfun(@times,B,A),m,n,ones(1,M/m),ones(1,N/n))));
If you have the image processing toolbox, you can try blkproc
:
>> A = magic(4)
A =
16 2 3 13
5 11 10 8
9 7 6 12
4 14 15 1
>> B = [1 0; 0 0];
>> C = blkproc(A,size(B),@(x) x.*B)
C =
16 0 3 0
0 0 0 0
9 0 6 0
0 0 0 0