R语言 词汇范围

R语言 词汇范围

R编程中的词法范围意味着自由变量的值是在定义函数的环境中搜索的。一个环境是一个符号、值和对的集合,每个环境都有一个父环境,一个环境有可能有多个子环境,但唯一没有父环境的环境是空环境。如果符号的值在定义函数的环境中找不到,那么就在父环境中继续搜索。在R中,自由变量的绑定是通过首先在创建函数的环境中寻找来解决的。这就是所谓的 词汇范围。

为什么是词法范围

词汇范围是一组规则,它有助于确定R如何表示一个符号的值。它是R中的一个内置规则,在语言层面上自动工作。它主要用于指定统计计算。词法范围是根据函数创建时的初始嵌套方式来查找符号,而不是根据函数被调用时的嵌套方式来查找。当我们使用词法范围时,我们不需要知道函数是如何被调用的,也不需要弄清楚变量的值将在哪里被查看。我们只需要看一下函数的定义。

词法范围中的词法含义与通常的英语定义完全不同,后者是指与语言中的单词或词汇有关,与语法和结构相区别,而它来自计算机科学术语 “词法”,意思是将文本表示的代码转换为编程语言可以理解的有意义的片段的过程。请看下面的例子。

f <- function(x, y)
{
  x * y * z
}
R

在此。

  • x和y是形式参数
  • z为自由变量

因此,语言的作用域规则决定了如何向自由变量赋值。自由变量不是形式参数,也不是在函数体内部分配的局部变量。

词汇范围的原则

R语言实现词法范围的背后有四个基本原则。

  1. 名称屏蔽
  2. 函数与变量
  3. 重新开始
  4. 动态查找

让我们逐一讨论每个原则。

名称屏蔽

下面的例子说明了词法范围的最基本原则,你应该不难预测其输出。

  • 如果变量没有在函数中定义:

示例:

c <- 10
f <- function(a, b)
{
  a + b + c
}
f(8, 5) 
R

输出:

[1] 23
R

它将c值作为10,然后将这些数字相加,最后我们的输出是23。

  • 如果名字没有在函数内定义:
    如果一个名字没有在一个函数中定义,R会向上看一层。

示例:

a <- 10
b <- function()
{
  c <- 11
  c(a, c)
}
b() 
R

输出:

[1] 10 11
R
  • 当一个函数被定义在另一个函数里面时:

    如果一个函数被定义在另一个函数里面,同样的规则也适用:先看当前函数,然后看该函数被定义的地方,以此类推,一直到全局环境,然后再看其他加载的包。

示例:

a <- 10
g <- function(){
  b <- 20
  h <- function(){
    c <- 30
    c(a, b, c) 
  }
  h()
}
g()
R

输出:

[1] 10 20 30
R
  • 当函数由另一个函数创建时:
    同样的规则适用于闭包、由其他函数创建的函数。

示例:

a <- function(z){
  b <- 10
  function(){
    z + 4 * b
  }
}
x <- a(10)
x() 
R

输出:

[1] 50
R

R在调用函数后返回b的准确值,因为x保留了它被定义的环境。该环境包括b的值。

函数与变量

无论关联值的类型如何,同样的原则都适用–寻找函数的方法与寻找变量的方法完全相同:

例子

a <- function(x) 10 * x
b <- function(){
  a <- function(x) x + 10
  a(12)
}
b() 
R

输出

[1] 22
R

一个新的开始

当一个函数被调用时,每次都会创建一个新的环境。每次确认都是完全独立的,因为一个函数无法知道它上次运行时发生了什么。

例子

a <- function(){
  if(!exists("z"))
  {
    z <- 10
  }
  else
  {
    z <- z+10
  }
  z
}
a()
R

输出

[1] 10
R

动态查找

词汇范围控制的是在哪里找值,而不是什么时候找值。R在执行函数的时候寻找数值,而不是在创建函数的时候寻找数值。该函数的输出可以根据其环境之外的对象而有所不同。

例子

g <- function() x^3
x <- 10
g() 
R

输出

[1] 1000
R

在R中,有一个函数是来自 codetoolsfindGlobals( ),它可以帮助我们找到一个函数中使用的所有全局变量,并列出一个函数的所有外部依赖关系。 findGlobals() 可以找到全局变量和被闭包使用的函数。

aGlobal <- rnorm(10)
bGlobal <- rnorm(10)
  
f <- function()
{ 
  a <- aGlobal
  b <- bGlobal
  plot(b ~ a)
}
codetools::findGlobals(f) 
R

输出

[1] "{"       "~"       "<-"      "aGlobal" "bGlobal" "plot"
R

我们可以手动将环境改为空环境 emptyenv() 。emptyenv() 是一个完全的空环境。

Python教程

Java教程

Web教程

数据库教程

图形图像教程

大数据教程

开发工具教程

计算机教程

登录

注册