Глобальные и локальные переменные в R



Я новичок в R, и я совершенно запутался с использованием локальных и глобальных переменных в р.



Я читал некоторые сообщения в интернете, которые говорят, если я использую = или <- Я назначу переменную в текущей среде, и с <<- Я могу получить доступ к глобальной переменной внутри функции.



однако, как я помню, в C++ локальные переменные возникают всякий раз, когда вы объявляете переменную внутри скобок {}, так что мне интересно, если это то же самое для R? Или это только для функции в R, что у нас есть понятие локальных переменных.



Я сделал небольшой эксперимент, который, кажется, предполагает, что только скобки не достаточно, я получаю что-то не так?



{
x=matrix(1:10,2,5)
}
print(x[2,2])
[1] 4
627   3  
r

3 ответов:

переменные, объявленные внутри функции являются локальными к этой функции. Например:

foo <- function() {
    bar <- 1
}
foo()
bar

выдает следующую ошибку: Error: object 'bar' not found.

если вы хотите сделать bar глобальная переменная, вы должны сделать следующее:

foo <- function() {
    bar <<- 1
}
foo()
bar

в этом случае bar доступно извне функции.

однако, в отличие от C, C++ и многих других языков, скобки не определяют объем переменных. Например, в следующем коде фрагмент:

if (x > 10) {
    y <- 0
}
else {
    y <- 1
}

y остается доступным после if-else заявление.

как вы хорошо говорите, вы также можете создавать вложенные среды. Вы можете посмотреть на эти две ссылки для понимания того, как их использовать:

  1. http://stat.ethz.ch/R-manual/R-devel/library/base/html/environment.html
  2. http://stat.ethz.ch/R-manual/R-devel/library/base/html/get.html

здесь у вас есть небольшой пример:

test.env <- new.env()

assign('var', 100, envir=test.env)
# or simply
test.env$var <- 100

get('var') # var cannot be found since it is not defined in this environment
get('var', envir=test.env) # now it can be found

<- делает назначение в современных условиях.

когда вы находитесь внутри функции R создает новую среду для вас. По умолчанию он включает в себя все из среды, в которой он был создан, поэтому вы можете использовать эти переменные, но все новое, что вы создаете, не будет записано в глобальную среду.

В большинстве случаев <<- назначит переменные уже в глобальной среде или даже создаст переменную в глобальной среде если вы находитесь внутри функции. Однако, это не совсем так просто, как это. Что он делает, это проверяет родительскую среду для переменной с именем интереса. Если он не находит его в вашей родительской среде, он переходит к родителю родительской среды (в момент создания функции) и ищет там. Он продолжает восходить к глобальной среде, и если он не найден в глобальной среде, он назначит переменную в глобальной среде.

этот может проиллюстрировать, что происходит.

bar <- "global"
foo <- function(){
    bar <- "in foo"
    baz <- function(){
        bar <- "in baz - before <<-"
        bar <<- "in baz - after <<-"
        print(bar)
    }
    print(bar)
    baz()
    print(bar)
}
> bar
[1] "global"
> foo()
[1] "in foo"
[1] "in baz - before <<-"
[1] "in baz - after <<-"
> bar
[1] "global"

в первый раз, когда мы печатаем бар, мы не позвонили foo тем не менее, он все равно должен быть глобальным - это имеет смысл. Во второй раз мы печатаем это внутри foo перед вызовом baz так что значение "в foo" имеет смысл. Ниже мы видим, что <<- на самом деле делает. Следующее напечатанное значение- " in baz-before <<-. Это потому что <<- не смотрит в текущая среда (если вы не находитесь в глобальной среде, в этом случае <<- действует как <-). Так что внутри baz значение бара остается как "в baz-before baz копия бара внутри foo меняется на "В баз", но, как мы видим, глобальный bar остается неизменной. Это потому, что копия bar это определяется внутри foo есть в родительской среде, когда мы создали baz Итак, это первый экземпляр bar это <<- видит и, таким образом, копия, которую он назначает. Так что <<- это не просто прямое назначение глобальной среде.

<<- сложно, и я бы не рекомендовал использовать его, если вы можете избежать этого. Если вы действительно хотите назначить глобальную среду, вы можете использовать функцию assign и явно указать ей, что вы хотите назначить глобально.

теперь я меняю <<- для оператора assign и мы можем видеть, какой эффект это имеет:

bar <- "global"
foo <- function(){
    bar <- "in foo"   
    baz <- function(){
        assign("bar", "in baz", envir = .GlobalEnv)
    }
    print(bar)
    baz()
    print(bar)
}
bar
#[1] "global"
foo()
#[1] "in foo"
#[1] "in foo"
bar
#[1] "in baz"

так что оба раза мы печатаем бар внутри foo значение "в foo" даже после вызова baz. Это потому что assign никогда даже не рассматривал копию bar внутри foo, потому что мы сказали ему, где именно искать. Однако на этот раз значение bar в глобальной среде было изменено, потому что мы явно назначили там.

теперь вы также спросили о создании локальных переменных, и вы можете сделать это довольно легко, а также без создания функции... Нам просто нужно использовать local функция.

bar <- "global"
# local will create a new environment for us to play in
local({
    bar <- "local"
    print(bar)
})
#[1] "local"
bar
#[1] "global"

немного больше по тем же линиям

attrs <- {}

attrs.a <- 1

f <- function(d) {
    attrs.a <- d
}

f(20)
print(attrs.a)

выведет "1"

attrs <- {}

attrs.a <- 1

f <- function(d) {
   attrs.a <<- d
}

f(20)
print(attrs.a)

печать "20"

Comments

    Ничего не найдено.