猿问

为什么R中循环慢?

我知道循环很慢R我应该试着用一种矢量化的方式去做事情。

但是,为什么?为什么循环慢apply是快吗?apply调用几个子函数-看起来不太快。

最新情况:很抱歉,这个问题是不恰当的。我把矢量化和apply..我的问题应该是,

“为什么矢量化更快?”



ibeautiful
浏览 545回答 3
3回答

胡说叔叔

R中的循环是慢的,因为任何解释的语言都是慢的:每一次操作都会带来很多额外的负担。看R_execClosure在……里面eval.c(这是调用用户定义函数的函数)。它有近100行长,并执行各种操作-创建用于执行的环境,将参数分配到环境中,等等。想一想,在C中调用函数(将args推到堆栈、跳转、弹出args)时发生的事情要少得多。这就是为什么你会得到这样的时间安排(正如joran在评论中指出的那样,这实际上不是apply这太快了,这是内部C循环mean太快了。apply只是普通的旧R码):A&nbsp;=&nbsp;matrix(as.numeric(1:100000))使用循环:0.342秒:system.time({ &nbsp;&nbsp;&nbsp;&nbsp;Sum&nbsp;=&nbsp;0 &nbsp;&nbsp;&nbsp;&nbsp;for&nbsp;(i&nbsp;in&nbsp;seq_along(A))&nbsp;{ &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Sum&nbsp;=&nbsp;Sum&nbsp;+&nbsp;A[[i]] &nbsp;&nbsp;&nbsp;&nbsp;} &nbsp;&nbsp;&nbsp;&nbsp;Sum})使用SUM:无法测量的小:sum(A)这有点令人不安,因为,渐近地说,循环就像sum没有任何实际的理由,它应该是缓慢的,它只是做更多的额外工作,每次迭代。因此,请考虑:#&nbsp;0.370&nbsp;secondssystem.time({ &nbsp;&nbsp;&nbsp;&nbsp;I&nbsp;=&nbsp;0 &nbsp;&nbsp;&nbsp;&nbsp;while&nbsp;(I&nbsp;<&nbsp;100000)&nbsp;{ &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;10 &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;I&nbsp;=&nbsp;I&nbsp;+&nbsp;1 &nbsp;&nbsp;&nbsp;&nbsp;}})#&nbsp;0.743&nbsp;seconds&nbsp;--&nbsp;double&nbsp;the&nbsp;time&nbsp;just&nbsp;adding&nbsp;parenthesessystem.time({ &nbsp;&nbsp;&nbsp;&nbsp;I&nbsp;=&nbsp;0 &nbsp;&nbsp;&nbsp;&nbsp;while&nbsp;(I&nbsp;<&nbsp;100000)&nbsp;{ &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;((((((((((10)))))))))) &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;I&nbsp;=&nbsp;I&nbsp;+&nbsp;1 &nbsp;&nbsp;&nbsp;&nbsp;}})(这个例子是由拉德福德·尼尔)因为(在R中是一个运算符,实际上每次使用它时都需要一个名称查找:>&nbsp;`(`&nbsp;=&nbsp;function(x)&nbsp;2>&nbsp;(3)[1]&nbsp;2或者,一般来说,解释操作(在任何语言中)都有更多的步骤。当然,这些步骤也提供了好处:你不能做那,那个(在C.

芜湖不芜

循环不是总是慢的,而且apply是快速的。对此有一个很好的讨论2008年5月,R新闻杂志:尤伊·利格斯和约翰·福克斯。服务台:我怎样才能避免这个循环,或者让它更快?r新闻,8(1):46-50,2008年5月。在“循环!”(从第48页开始),他们说:许多关于R状态的评论认为使用循环是一个特别糟糕的主意。这不一定是真的。在某些情况下,很难编写向量化代码,或者向量化代码可能会消耗大量内存。他们还建议:在循环之前将新对象初始化为完整长度,而不是在循环中增加它们的大小。不要在循环中做可以在循环之外完成的事情。不要为了避免循环而避免循环。他们有一个简单的例子,其中for循环需要1.3秒,但是apply内存耗尽了。
随时随地看视频慕课网APP
我要回答