我的问题:我注意到,关于SO的Matlab问题的很多很好的答案经常使用bsxfun
函数。为什么?
动机:在Matlab文档bsxfun
中,提供了以下示例:
A = magic(5);
A = bsxfun(@minus, A, mean(A))
当然,我们可以使用以下方法执行相同的操作:
A = A - (ones(size(A, 1), 1) * mean(A));
实际上,简单的速度测试表明第二种方法的速度提高了约20%。那么为什么要使用第一种方法呢?我猜在某些情况下,使用
bsxfun
会比“手动”方法快得多。我真的很想看到这种情况的示例,并解释为什么它更快。同样,这个问题的最后一个元素,同样来自Matlab文档中的
bsxfun
:“C = bsxfun(fun,A,B)将由函数handle fun指定的逐元素二进制操作应用于数组A和B,其中单例扩展已启用。”。短语“启用单例扩展已启用”是什么意思? 最佳答案
我使用bsxfun
的三个原因(documentation,blog link)
bsxfun
比repmat
更快(见下文)bsxfun
需要更少的键入bsxfun
就像使用accumarray
一样,使我对Matlab的理解感到很好。 bsxfun
将沿输入数组的“单维度”(即数组的大小为1的维度)复制输入数组,以便它们与另一个数组的相应维度的大小匹配。这就是所谓的“单子(monad)展开”。顺便说一句,如果您调用squeeze
,则将删除单例尺寸。对于很小的问题,
repmat
方法可能会更快-但在该数组大小下,两个操作都非常快,以至于在整体性能方面不会有任何不同。 bsxfun
速度更快有两个重要原因:(1)计算是在编译后的代码中进行的,这意味着数组的实际复制将永远不会发生;(2)bsxfun
是多线程Matlab函数之一。我在相当快的笔记本电脑上使用R2012b在
repmat
和bsxfun
之间进行了速度比较。对我来说,
bsxfun
大约比repmat
快3倍。如果数组变大,则差异会更加明显repmat
运行时的跳转发生在数组大小为1Mb左右,这可能与我的处理器缓存的大小有关-bsxfun
的跳转没有那么糟糕,因为它只需要分配输出数组。在下面可以找到我用于计时的代码:
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
关于arrays - 在Matlab中,何时最佳使用bsxfun?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/12951453/