There are three reasons I use bsxfun
(documentation, blog link)
bsxfun
is faster thanrepmat
(see below)bsxfun
requires less typing- Using
bsxfun
, like usingaccumarray
, makes me feel good about my understanding of MATLAB.
bsxfun
will replicate the input arrays along their “singleton dimensions”, i.e., the dimensions along which the size of the array is 1, so that they match the size of the corresponding dimension of the other array. This is what is called “singleton expansion“. As an aside, the singleton dimensions are the ones that will be dropped if you call squeeze
.
It is possible that for very small problems, the repmat
approach is faster – but at that array size, both operations are so fast that it likely won’t make any difference in terms of overall performance. There are two important reasons bsxfun
is faster: (1) the calculation happens in compiled code, which means that the actual replication of the array never happens, and (2) bsxfun
is one of the multithreaded MATLAB functions.
I have run a speed comparison between repmat
and bsxfun
with MATLAB R2012b on my decently fast laptop.
For me, bsxfun
is about three times faster than repmat
. The difference becomes more pronounced if the arrays get larger:
The jump in runtime of repmat
happens around an array size of 1 MB, which could have something to do with the size of my processor cache – bsxfun
doesn’t get as bad of a jump, because it only needs to allocate the output array.
Below you find the code I used for timing:
n = 300;
k=1; %# k=100 for the second graph
a = ones(10,1);
rr = zeros(n,1);
bb = zeros(n,1);
ntt = 100;
tt = zeros(ntt,1);
for i=1:n;
r = rand(1,i*k);
for it=1:ntt;
tic,
x = bsxfun(@plus,a,r);
tt(it) = toc;
end;
bb(i) = median(tt);
for it=1:ntt;
tic,
y = repmat(a,1,i*k) + repmat(r,10,1);
tt(it) = toc;
end;
rr(i) = median(tt);
end