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

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

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

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

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

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

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

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

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

Если вы хотите сделать bar глобальной переменной, вы должны сделать:

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

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

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

 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 поэтому значение «in foo» имеет смысл. Ниже мы видим, что на самом деле делает <<- . Следующее значение, напечатанное «baz - before << -», даже если инструкция печати появляется после <<- . Это потому, что <<- не выглядит в текущей среде (если вы не находитесь в глобальной среде, в этом случае <<- действует как <- ). Таким образом, внутри baz значение bar остается как «в baz - до << -». Как только мы вызываем baz копия бара внутри foo меняется на «baz», но, как мы видим, глобальный bar не изменяется. Это связано с тем, что копия bar которая определена внутри foo находится в родительской среде, когда мы создали baz так что это первая копия bar которую <<- видит и, следовательно, копирует ее. Таким образом, <<- это не просто непосредственное назначение глобальной среде.

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

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

 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"

  • Создать таблицу PDF
  • Сплит-кадр данных по уровням фактора и именных кадров данных по этим уровням
  • Возвращаемый индекс наименьшего значения в векторе?
  • Вычисление суммарной суммы для каждой строки
  • Как увеличить количество столбцов с помощью R в Linux
  • Использование gsub для извлечения символьной строки перед пробелом в R
  • R - вырезание с помощью заданного интервала
  • Подавить вывод одной команды в R
  • Стандартный способ удаления нескольких элементов из фрейма данных
  • Какой самый полезный трюк?
  • вытащить p-значения и r-квадрат из линейной регрессии
  • Давайте будем гением компьютера.