Присвойте динамическую функцию глобальной среде в R - PullRequest
0 голосов
/ 01 июля 2018

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

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

Пожалуйста, проверьте этот код, чтобы понять мой вопрос:

set.seed(123)
ds <- data.frame(income=rnorm(1000,700,20), sex=c(0,1), age=rnorm(1000,30,10))

regress <- function(iv_string) {
  regression_formula <- as.formula(paste("income ~", iv_string))
  results <<- lm(regression_formula, ds)
  plot(results)
  print(results)
}
regress("age")
regress("sex")

Нечто подобное

  regress <- function(iv_string, **custom_name**) {
      regression_formula <- as.formula(paste("income ~", iv_string))
      results[**custom_name**] <<- lm(regression_formula, ds)
      plot(results)
      print(results)
    }
regress("sex","sex_on_income") #this model will be used in other analysis, once it will be assigned at global environment
regress("age","age_on_income") #this model will be used !!

final solution Большое спасибо.

Ответы [ 2 ]

0 голосов
/ 01 июля 2018

Это запишет объект lm в родительский фрейм или другое окружение, указанное в env, нанесет его на график, напечатает и невидимо вернет. Также мы удостоверимся, что среда формулы равна env, что позволяет iv_string ссылаться на объекты в env, а также на столбцы в ds. (Если бы мы знали, что iv_string ссылается только на имена столбцов в ds, то мы могли бы просто использовать fo <- paste("income ~", iv_string), так как lm будет принимать символьные строки в качестве формул.) Мы используем do.call(...), чтобы обеспечить вывод lm показывает фактическую формулу, а не просто fo. Мы использовали родительский фрейм в качестве значения по умолчанию для env, что более привычно, но если вы действительно хотите, чтобы значением по умолчанию было глобальное окружение, замените parent.frame() на .GlobalEnv или globalenv().

regress <- function(iv_string, custom_name = iv_string, env = parent.frame()) {
  fo <- as.formula(paste("income ~", iv_string), env)
  env[[custom_name]] <- results <- do.call("lm", list(fo, quote(ds)))
  plot(results)
  print(results)
  invisible(results)
}

regress("age", "lm_age")

дает:

Call:
lm(formula = income ~ age, data = ds)  <-- note that formula shows, not just fo

Coefficients:
(Intercept)          age  
   695.1540       0.1699  

Тем не менее, обычный стиль в R - это не запись объектов в родительский фрейм или в глобальную среду, а их возврат:

regress <- function(iv_string, env = parent.frame()) {
  fo <- as.formula(paste("income ~", iv_string), env)
  results <- do.call("lm", list(fo, quote(ds)))
  plot(results)
  print(results)
  invisible(results)
}

lm_age <- regress("age")
0 голосов
/ 01 июля 2018

Вот модифицированная версия вашего кода, которую я думаю дает вам, что вы хотите.

regress <- function(iv_string, custom_name) {
  regression_formula <- as.formula(paste("income ~", iv_string))
  assign(custom_name, lm(regression_formula, ds), envir = .GlobalEnv)
  plot(get(custom_name))
  print(get(custom_name))
}

regress("age", "age_reg")

В приведенном выше коде I assign регрессия приводит к глобальной переменной, определяемой строкой custom_name. Для операторов plot и print я использую get, чтобы получить переменную, названную в этой строке, и передать ее этим функциям. Итак, в моем примере он создаст графики и напечатает результаты, а переменная с именем age_reg появится в глобальной среде и будет содержать результаты регрессии.

...