我经常在这里发布的很多答案中发现大量使用纯函数,而且这些解决方案通常比使用命名模式快得多.为什么会这样?为什么纯函数比其他函数更快?是否与mma口译员必须做的工作有关?
首先,让我们考虑一些示例基准:
In[100]:= f[x_]:=x^2;
In[102]:= Do[#^2&[i],{i,300000}]//Timing
Out[102]= {0.406,Null}
In[103]:= Do[f[i],{i,300000}]//Timing
Out[103]= {0.484,Null}
In[104]:= Do[Function[x,x^2][i],{i,300000}]//Timing
Out[104]= {0.578,Null}
Run Code Online (Sandbox Code Playgroud)
由于两个原因,纯函数通常(更快)更快.首先,匿名纯函数(使用插槽定义的函数 - #
和&
)不需要解析变量名称的名称冲突.因此,它们比模式定义的更快,其中发生了一些名称冲突解决.但是你会发现带有命名变量的纯函数实际上比模式定义的更慢,而不是更快.我可以推测这是因为他们还必须解决他们体内可能发生的冲突,而基于规则的冲突则忽略了这些冲突.在任何情况下,速度差异大约为10-20%.
另一个更为戏剧性的区别在于它们用于Map,Scan,Table等功能,因为后者在大型数字(打包)列表上自动编译.但是,虽然通常可以编译纯函数,但模式定义的函数基本上不能,因此它们无法访问这种速度增益.例如:
In[117]:= ff[x_] := Sqrt[x];
In[116]:= Map[Sqrt[#] &, N@Range[100000]]; // Timing
Out[116]= {0.015, Null}
In[114]:= Map[ff, N@Range[100000]]; // Timing
Out[114]= {0.094, Null}
Run Code Online (Sandbox Code Playgroud)