打开APP
userphoto
未登录

开通VIP,畅享免费电子书等14项超值服

开通VIP
R语言中”<-”和”=”的差异本质
本帖最后由 李振德 于 2012-10-9 15:29 编辑
第一篇: 学习R语言中”<-”和”=”的差异本质
参考相关资源如下:
1、http://bbs.pinggu.org/thread-1247151-1-1.html
2、http://yihui.name/cn/2012/09/equal-and-arrow/
3、http://f.dataguru.cn/forum.php?m ...824&page=2#pid87934   4、http://cran.r-project.org/doc/manuals/R-lang.html#Argument-matching
参考资源的作用
1、有关 ”<-”和”=”文档的权威解释
2、有关 ”<-”和”=”文档的历史、解释、实例等
3、有关 ”<-”和”=” 使用区别
4、有关函数中参数命名的权威解释
参考资源的原文如下:
1、 原发布作者 daxia101
What’s thedifference?
The maindifference between the two assignment operators is scope. It’seasiest to see the difference with an example:
##Delete x(if it exists)
>rm(x)
>mean(x=1:10) #[1] 5.5
> x#Error: object 'x' not found
Here x isdeclared within the function’s scope of the function, so it doesn’texist in the user workspace. Now, let’s run the same piece of codewith using the <- operator:
> mean(x<- 1:10)# [1] 5.5
> x # [1]1 2 3 4 5 6 7 8 9 10
This time thex variable is declared within the user workspace.
When does theassignment take place?
In the codeabove, you may be tempted to thing that we “assign 1:10 to x, thencalculate the mean.” This would be true for languages such as C,but it isn’t true in R. Consider the following function:
> a <-1
> f <-function(a) return(TRUE)
> f <-f(a <- a + 1); a
[1]TRUE
[1]1
Notice thatthe value of a hasn’t changed! In R, the value of a will onlychange if we need to evaluate the argument in the function. Thiscan lead to unpredictable behaviour:
> f <-function(a) if(runif(1)>0.5) TRUE else a
> f(a<- a+1);a
[1]2
> f(a<- a+1);a
[1]TRUE
[1]2
> f(a<- a+1);a
[1]3
------------------------------
2、原发布作者:
赋值
赋值符号在绝大多数语言中都没什么好讨论的,因为就是一个等号而已。在R社区,这一点却被讨论来讨论去,主要原因是箭头赋值符号<-的存在。箭头来源于贝尔实验室早年的某台古董机器上有一个下划线的键,但打出来显示的是箭头。S祖先们认为箭头是一个很形象的赋值符号,于是下划线被采纳下来,甚至后来衍生出右箭头(->)这样更奇怪的赋值符号(表示把左边的值赋给右边的变量),还有双箭头(<<-)表示给上一层环境中的变量赋值。
最初S代码中,下划线本身就是赋值符号,例如x_1表示把1赋值给x。我大三的时候还用S-Plus写了不少下划线赋值的S代码。后来Rcore们做了一个艰难的决定,允许等号作为赋值符号,废弃了下划线的赋值功能,但下划线的传统仍然无处不在,例如Emacs /ESS中默认情况下敲下划线会被替代为左箭头(为了得到真的下划线需要连续按两次下划线),尽管下划线本身已经不能直接显示为箭头,ESS仍然想昨日重现,通过软件方式强行替代之。
我不止一次地说过,我是坚定的等号党。因为等号有赋值功能,大多数语言都用等号(没见其它语言的程序员抱怨等号不形象),等号对我来说不存在歧义,让我的代码更安全。反对党(也就是箭头党)的理由通常是等号存在二义性:它既可以赋值,也可以传递函数参数,如:
x = 1:10
length(x = 1:10)
可是几乎所有语言都这样,也没有见那些语言的程序员对此有抱怨。规则很简单:如果等号出现在单独的环境中,它就是赋值;如果写在函数参数位置,它就是传参数。但R的古怪让这个简单规则也可以变得很难判断,例如:
length((x = 1:10))
length({x = 1:10})
因为()和{}将表达式与外面的环境隔离开来,它们被解析的时候先单独运行,所以实际上x在自己的环境里被赋值了;然后()和{}会返回整个表达式的结果,这个结果再传给length()函数。
箭头在任何地方的意思都是赋值(在当前环境下),它可以被写在任何地方,包括函数参数的位置,如:
length(x <- 1:10)
这句代码先对x赋值,然后把整个表达式的值传递给length()。我们可以把它写得更晕:
length(x = y <- 1:10)
此时等号表示传参数,而y无论如何都会被赋值。在函数参数位置上赋值通常有一举两得的效果,也就是把两件事情写在一行上,之所以能一举两得,主要是利用了箭头的副作用;如果是初学者,这种写法最好避免,首先追求代码的清晰性,避免产生副作用的代码。因为箭头无论何地都可以赋值,要是用错了也不会报错,这种错误往往难以意识到。例如我们创建一个向量,元素为1和2,元素名字分别为a和b,如果不小心写成这样:
c(a = 1, b <- 2)  # 本来应该是c(a =1, b = 2)
你可能不会意识到第二个元素是没有名字的,并且这句话带来一个副作用,就是悄悄给b赋了值。
如果你像我一样有时候写代码不爱打空格,那么还有一个更可怕的潜在错误,要是不小心犯了的话可能很久都查不出来。我们写几个逻辑表达式:x大于5,x小于3,x小于-3。你可能想,这个太简单了,操起键盘就写:
x>5
x<3
x<-3
因为你的懒惰,小于号和负号悄磨叽走到了一起,不小心形成了具有强大法力的赋值箭头,你并没有完成x与-3的逻辑大小比较,而是给x赋值为3。当这几行代码在这里摆着的时候你可能觉得很容易看出来,可是当你玩了两个小时数据之后,想随手看一下df数据框中x变量小于-1的值有多少个,你可能会写出sum(df$x<-1)这样的语句,相应的结果是,你没得到df$x小于-1的总数,而是把df数据里x这一列给修改为1了。如果df是一个很大的数据,或你辛辛苦苦处理了半天才得来的数据,你就哭吧。我对这个诡异的案例印象深刻,是因为我亲眼看见过两例别人的错误,在那之后我明知有这样的危险,但自己还是傻不愣登毁了一次自己的数据。
对右箭头赋值,我的想象是这样:某天某祖先写了一长段代码,但没有事先写上把这段代码的结果赋值保留下来,悔得肠子都青了,只好敲回车任凭程序在那儿跑,跑完了得不到返回值,于是该祖先发明了一个右箭头,这样即使先写了一段代码也不用怕,因为可以最后加上->x就把前面的返回值赋给x了。我不习惯阅读这种事后赋值的代码,就像读侦探小说似的,到最后才发现代码创建了一个变量。
这种“后悔”的想象还可以继续:R中有一个特殊的变量叫.Last.value,它总是保存最近一次运行的最后一个结果,即使你上一条代码没有赋值保存,你仍然可以通过.Last.value去获取。这也意味着,无论你跑什么程序,R都会随时盯着你的返回结果,把它赋值给.Last.value。
--------------------------------------------------------
3、两者在某些时候是有区别的
可以认为”<-”是赋值,”=”是传值
在函数调用中,func(x=1)与func(x<-1)是有区别的,前者调用完后变量x不会被保留,而后者会在工作区里保留变量x=1。
比如length(x=seq(1,10))计算完成后x不会被保留,而length(x<-seq(1,10))计算完后你会在工作区里发现x这个变量
-------------------------------------------------------
4、 原文  发布者  官方文档 4.3.2Argument matching
This subsection appliesto closures but not to primitive functions. The latter typicallyignore tags and do positional matching, but their help pages shouldbe consulted for exceptions, which include log, round, signif, repandseq.int.
The first thing thatoccurs in a function evaluation is the matching of formal to theactual or supplied arguments. This is done by a three-passprocess:
Exactmatching on tags. For each named supplied argument thelist of formal arguments is searched for an item whose name matchesexactly. It is an error to have the same formal argument matchseveral actuals or vice versa.
Partialmatching on tags. Each remaining named supplied argumentis compared to the remaining formal arguments using partialmatching. If the name of the supplied argument matches exactly withthe first part of a formal argument then the two arguments areconsidered to be matched. It is an error to have multiple partialmatches. Notice that if f <- function(fumble, fooey) fbody, thenf(f = 1, fo = 2) is illegal, even though the 2nd actual argumentonly matches fooey. f(f = 1, fooey =2) is legalthough since the second argument matches exactly and is removedfrom consideration for partial matching. If the formal argumentscontain ‘...’ then partial matching is only applied to argumentsthat precede it.
Positionalmatching. Any unmatched formal arguments are boundto unnamed suppliedarguments, in order. If there is a ‘...’ argument, it will take upthe remaining arguments, tagged or not.
If any arguments remainunmatched an error is declared.
Argument matching isaugmented by the functions match.arg, match.call and match.fun.Access to the partial matching algorithm used by R is viapmatch.
其实:这4篇已经很好的解释了  ”<-”和”=”  的差异了
本站仅提供存储服务,所有内容均由用户发布,如发现有害或侵权内容,请点击举报
打开APP,阅读全文并永久保存 查看更多类似文章
猜你喜欢
类似文章
【热】打开小程序,算一算2024你的财运
The R language, for programmers
Can Your Programming Language Do This?
2.3 函数II(Functions II)
函数指针数组的定义
C#学习记录001---visual studio 2010
PHP函数
更多类似文章 >>
生活服务
热点新闻
分享 收藏 导长图 关注 下载文章
绑定账号成功
后续可登录账号畅享VIP特权!
如果VIP功能使用有故障,
可点击这里联系客服!

联系客服