Performance Matlab bsxfun-为什么在这种情况下bsxfun无法工作?
我有一个二元函数,大致如下Performance Matlab bsxfun-为什么在这种情况下bsxfun无法工作?,performance,matlab,vectorization,bsxfun,Performance,Matlab,Vectorization,Bsxfun,我有一个二元函数,大致如下 func=@(i,j)exp(-32*(i-j)^2); 其网格如下所示 [X Y]=meshgrid(-10:.1:10); 奇怪的是,arrayfun会产生正确的结果,bsxfun会产生Inf的条目 an1=arrayfun(func,X,Y); an2=bsxfun(func,X,Y); >> max(max(abs(an1-an2))) ans = Inf 为什么? 编辑:现在问题已经解决了。我加入了一些基准数据,以便与bsx
func=@(i,j)exp(-32*(i-j)^2);
其网格如下所示
[X Y]=meshgrid(-10:.1:10);
奇怪的是,arrayfun
会产生正确的结果,bsxfun
会产生Inf
的条目
an1=arrayfun(func,X,Y);
an2=bsxfun(func,X,Y);
>> max(max(abs(an1-an2)))
ans =
Inf
为什么?
编辑:现在问题已经解决了。我加入了一些基准数据,以便与
bsxfun
假设网格已经用
[X Y]=meshgrid(Grid.partition);
func=@(i,j)exp(-32*(i-j).^2);
(我打算在不同的地方多次重复使用网格。)
使用嵌套命名函数方法计时
>> tic;for i=1:1000;temp3=exp(-32*bsxfun(@minus,Grid.partition.',Grid.partition).^2);end;toc,clear temp
Elapsed time is 1.473543 seconds.
>> tic;for i=1:1000;temp3=exp(-32*bsxfun(@minus,Grid.partition.',Grid.partition).^2);end;toc,clear temp
Elapsed time is 1.497116 seconds.
>> tic;for i=1:1000;temp3=exp(-32*bsxfun(@minus,Grid.partition.',Grid.partition).^2);end;toc,clear temp
Elapsed time is 1.816970 seconds.
匿名函数方法的计时
>> tic;for i=1:1000;temp=bsxfun(func,X,Y);end;toc,clear temp
Elapsed time is 1.134980 seconds.
>> tic;for i=1:1000;temp=bsxfun(func,X,Y);end;toc,clear temp
Elapsed time is 1.171421 seconds.
>> tic;for i=1:1000;temp=bsxfun(func,X,Y);end;toc,clear temp
Elapsed time is 1.180998 seconds.
可以看出,匿名函数方法比嵌套函数方法快(不包括meshgrid
上的时间)
如果包括meshgrid
上的时间
>> tic;[X Y]=meshgrid(Grid.partition);for i=1:1000;temp=bsxfun(func,X,Y);end;toc,clear X Y temp
Elapsed time is 1.965701 seconds.
>> tic;[X Y]=meshgrid(Grid.partition);for i=1:1000;temp=bsxfun(func,X,Y);end;toc,clear X Y temp
Elapsed time is 1.249637 seconds.
>> tic;[X Y]=meshgrid(Grid.partition);for i=1:1000;temp=bsxfun(func,X,Y);end;toc,clear X Y temp
Elapsed time is 1.208296 seconds.
很难说……与使用
bsxfun
的匿名函数不同,您可以这样做以更有效地使用bsxfun
-
arr1 = -10:.1:10
an2 = exp(-32*bsxfun(@minus,arr1.',arr1).^2)
标杆管理
这里试图澄清OP的运行时评论,以将bsxfun的匿名函数功能与内置的@减号进行比较,并进行一些基准测试
基准测试代码
func=@(i,j)exp(-32.*(i-j).^2);
num_iter = 1000;
%// Warm up tic/toc.
for k = 1:100000
tic(); elapsed = toc();
end
disp('---------------------------- Using Anonymous Functions with bsxfun')
tic
for iter = 1:num_iter
[X Y]=meshgrid(-10:.1:10);
an2=bsxfun(func,X,Y);
end
toc, clear X Y an2
disp('---------------------------- Using bsxfuns built-in "@minus"')
tic
for iter = 1:num_iter
arr1 = -10:.1:10;
an2 = exp(-32*bsxfun(@minus,arr1',arr1).^2);
end
toc
运行时
---------------------------- Using Anonymous Functions with bsxfun
Elapsed time is 0.241312 seconds.
---------------------------- Using bsxfuns built-in "@minus"
Elapsed time is 0.221555 seconds.
根据,当您使用任意函数func
调用bsxfun
时
func
必须能够接受大小相同的两个列向量或一个列向量和一个标量作为输入,并返回与输入大小相同的列向量作为输出
你的功能不能实现这一点。若要更正,请将^
替换为^
:
func=@(i,j)exp(-32*(i-j).^2);
无论如何,您可以使用bsxfun
的一个内置函数来代替函数(请参阅)。这样就避免了meshgrid
,代码可能会更快。是的,这一定是它的语法!测试。这就是原因。非常感谢。至于速度,我不认为命名函数更快。(在本例中进行了测试。正确的func
更快。我也曾在其他场景中体验过,Divakar建议的嵌套函数效率更低。)@Argyll但您至少可以避免meshgrid
。它应该更快。或者我就是这么想的thought@Argyll我对此深表怀疑。我和annonym一起工作。使用bsxfun
对之前的案例执行func操作。同样,正如Luis所说,您将避免在那里使用meshgrid
。像这样的嵌套函数效率不高。(更正后的func
更快。)但感谢您提供的arr1',arr1
语法。我非常希望避免使用meshgrid
@Argyll您测试的数据大小是多少?与示例中相同。201除了在meshgrid
@Argyll上的时间外,Anonymous大约快1.5倍。请查看刚才添加的基准测试代码,看看它在您这边的性能如何?arrayfun
总是慢得多。使用匿名函数尝试bsxfun
?正如Luis所指出的,meshgrid
也必须位于bsxfun
的匿名函数版本的tic tocs内,对吗<代码>bsxfun(@减号法一次完成了meshgrid
部分和函数部分的评估。我添加了包含meshgrid
时间的数据。它们是可比的。它们看起来确实是可比的!感谢您花时间放好所有这些!谢谢!!我很高兴学习所有这些。顺便说一句,我曾经制作过一个meshg去掉索引并应用我的二进制函数,比如@(i,j)exp(-32*partition(i)-partition(j))^2
。这太慢了。不再这样做了!所以,使用内置的@减号
?太棒了!