R 中未计算的参数
Unevaluated argument in R
我还是R的新手,对惰性求值还很了解。我在 SO (R functions that pass on unevaluated arguments to other functions) 上阅读了很多线程,但我仍然不确定。
问题一:
这是我的代码:
f <- function(x = ls()) {
a<-1
#x ##without x
}
f(x=ls())
当我执行此代码时,即 f()
,什么也没有 returns。具体来说,我没有看到 a
的值。为什么会这样?
问题二:
此外,我确实在这段代码中看到了 a
的值:
f <- function(x = ls()) {
a<-1
x ##with x
}
f(x=ls())
当我通过 f()
执行函数时,我得到:
[1] "a" "x"
为什么会这样?有人可以帮我吗?
问题一
这与惰性求值无关。
一个函数return是它执行的最后一条语句的结果。在这种情况下,最后一条语句是 a <- 1
。 a <- 1
的结果是 1。例如,您可以执行 b <- a <- 1
,这将导致 b
等于 1。因此,在这种情况下,您的函数是 returns 1。
> f <- function(x = ls()) {
+ a<-1
+ }
> b <- f(x=ls())
> print(b)
[1] 1
参数x
没有被使用,所以没有任何作用。
函数可以 return 可见(默认)或不可见的值。为了 return 不可见,可以使用函数 invisible
。一个例子:
> f1 <- function() {
+ 1
+ }
> f1()
[1] 1
>
> f2 <- function() {
+ invisible(1)
+ }
> f2()
>
在这种情况下 f2
似乎 return 什么都没有。但是,它仍然是 return 的值 1。invisible 所做的是在调用函数时不打印任何内容,并且结果未分配给任何内容。与您的示例相关的是 a <- 1
也 return 是无形的。这就是您的函数似乎没有 return 任何内容的原因。但是当赋值给上面的b
时,b
仍然得到值1。
问题二
首先,我将解释为什么您会看到您看到的结果。您在结果中看到的 a
是由之前的一些代码引起的。如果我们先清理工作区,我们只会看到 f
。这是有道理的,因为我们创建了一个变量 f
(函数在 R 中也是一个变量),然后执行 ls()
。
> rm(list = ls())
>
> f <- function(x = ls()) {
+ a<-1
+ x
+ }
> f(x=ls())
[1] "f"
函数的作用(至少是您所期望的),如果首先列出所有变量 ls()
然后将结果作为 x
传递给函数。这个函数然后 returns x
,这是所有变量的列表,然后被打印出来。
如何修改它以显示工作中的懒惰评估
> rm(list = ls())
>
> f <- function(x) {
+ a <<- 1
+ x
+ }
>
> f(x = ls())
[1] "a" "f"
>
在这种情况下,使用了全局赋值 (a <<- 1
),它在全局工作区中创建了一个新变量 a
(这不是您通常想要做的事情)。
在这种情况下,人们仍然希望函数调用的结果只是 f
。它也显示 a
的事实是由惰性评估引起的。
如果没有惰性求值,它将首先求值 ls()
(当时工作区中只有 f
),然后将其复制到名称为 x
的函数中。然后函数returns x
。在这种情况下, ls()
在创建 a
之前被评估。
但是,使用惰性求值,表达式 ls()
仅在需要表达式的结果时才求值。在这种情况下,即打印函数 returns 和结果时。那时全局环境发生了变化(创建了a
),也就是说ls()
也显示了a
。
(这也是您不希望函数使用 <<-
更改全局工作区的原因之一。)
我还是R的新手,对惰性求值还很了解。我在 SO (R functions that pass on unevaluated arguments to other functions) 上阅读了很多线程,但我仍然不确定。
问题一:
这是我的代码:
f <- function(x = ls()) {
a<-1
#x ##without x
}
f(x=ls())
当我执行此代码时,即 f()
,什么也没有 returns。具体来说,我没有看到 a
的值。为什么会这样?
问题二:
此外,我确实在这段代码中看到了 a
的值:
f <- function(x = ls()) {
a<-1
x ##with x
}
f(x=ls())
当我通过 f()
执行函数时,我得到:
[1] "a" "x"
为什么会这样?有人可以帮我吗?
问题一
这与惰性求值无关。
一个函数return是它执行的最后一条语句的结果。在这种情况下,最后一条语句是 a <- 1
。 a <- 1
的结果是 1。例如,您可以执行 b <- a <- 1
,这将导致 b
等于 1。因此,在这种情况下,您的函数是 returns 1。
> f <- function(x = ls()) {
+ a<-1
+ }
> b <- f(x=ls())
> print(b)
[1] 1
参数x
没有被使用,所以没有任何作用。
函数可以 return 可见(默认)或不可见的值。为了 return 不可见,可以使用函数 invisible
。一个例子:
> f1 <- function() {
+ 1
+ }
> f1()
[1] 1
>
> f2 <- function() {
+ invisible(1)
+ }
> f2()
>
在这种情况下 f2
似乎 return 什么都没有。但是,它仍然是 return 的值 1。invisible 所做的是在调用函数时不打印任何内容,并且结果未分配给任何内容。与您的示例相关的是 a <- 1
也 return 是无形的。这就是您的函数似乎没有 return 任何内容的原因。但是当赋值给上面的b
时,b
仍然得到值1。
问题二
首先,我将解释为什么您会看到您看到的结果。您在结果中看到的 a
是由之前的一些代码引起的。如果我们先清理工作区,我们只会看到 f
。这是有道理的,因为我们创建了一个变量 f
(函数在 R 中也是一个变量),然后执行 ls()
。
> rm(list = ls())
>
> f <- function(x = ls()) {
+ a<-1
+ x
+ }
> f(x=ls())
[1] "f"
函数的作用(至少是您所期望的),如果首先列出所有变量 ls()
然后将结果作为 x
传递给函数。这个函数然后 returns x
,这是所有变量的列表,然后被打印出来。
如何修改它以显示工作中的懒惰评估
> rm(list = ls())
>
> f <- function(x) {
+ a <<- 1
+ x
+ }
>
> f(x = ls())
[1] "a" "f"
>
在这种情况下,使用了全局赋值 (a <<- 1
),它在全局工作区中创建了一个新变量 a
(这不是您通常想要做的事情)。
在这种情况下,人们仍然希望函数调用的结果只是 f
。它也显示 a
的事实是由惰性评估引起的。
如果没有惰性求值,它将首先求值 ls()
(当时工作区中只有 f
),然后将其复制到名称为 x
的函数中。然后函数returns x
。在这种情况下, ls()
在创建 a
之前被评估。
但是,使用惰性求值,表达式 ls()
仅在需要表达式的结果时才求值。在这种情况下,即打印函数 returns 和结果时。那时全局环境发生了变化(创建了a
),也就是说ls()
也显示了a
。
(这也是您不希望函数使用 <<-
更改全局工作区的原因之一。)