2017-02-07 3 views
2

Я видел пример применения списка (lapply), который прекрасно работает, чтобы взять список объектов данных, и вернуть список регрессионного вывода, который мы можем пройти для Stargazer для хорошо отформатированного вывода. Using stargazer with a list of lm objects created by lapply-ing over a split data.frameИспользуйте множественную регрессию с изменением формулы, а не набор данных

library(MASS) 
library(stargazer) 
data(Boston) 

by.river <- split(Boston, Boston$chas) 
class(by.river) 

fit <- lapply(by.river, function(dd)lm(crim ~ indus,data=dd)) 
stargazer(fit, type = "text") 

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

fit2 <- vector(mode = "list", length = 2) 
fit2[[1]] <- lm(nox ~ indus, data = Boston) 
fit2[[2]] <- lm(crim ~ indus, data = Boston) 
stargazer(fit2, type = "text") 

с lapply, я попробовал это, и он не работает. Где я неправ?

myvarc <- c("nox","crim") 
class(myvarc) 
myvars <- as.list(myvarc) 
class(myvars) 
fit <- lapply(myvars, function(dvar)lm(dvar ~ indus,data=Boston)) 
stargazer(fit, type = "text") 
+0

Это работает, но не в чистом виде (использует номера столбцов не имена, не сохраняет имена для заголовков в выходные Звездочет) 'fit3 = lapply (Бостон [, c (1,5)], функция (x) (lm (x ~ Boston $ indus))) stargazer (fit3, type = "text") ' –

+0

Проблема решена ниже. Однако ярлыки не очень хорошо переносятся на Stargazer. Этот код исправит это. 'Stargazer (fit, type =" text ", dep.var.labels.include = FALSE, column.labels = myvarc)' –

ответ

0

Это должно работать:

fit <- lapply(myvars, function(dvar) lm(eval(paste0(dvar,' ~ wt')), data = Boston)) 
+0

Пока это работает так же, как Parfait's, 'as.formula' Parfait делает больше смысла читать. Однако я подозреваю, что использование более общего 'eval()' является более гибким и может быть полезным в некоторых других случаях. Cheers, –

+0

В R, 'eval (parse ...))', хотя здесь используется 'eval (paste0 (...))', но те же понятия для оценки строковых выражений обычно не рекомендуется по различным причинам (т. Е. Безопасность , согласованность). См. [Здесь] (http://stackoverflow.com/questions/13649979/what-specifically-are-the-dangers-of-evalparse) и [здесь] (http://stackoverflow.com/questions/1743698/evaluate- выражение данное-а-а-строки). – Parfait

+0

Спасибо за образование! Cheers, - –

3

Рассмотрите возможность создания динамических формул из строки:

fit <- lapply(myvars, function(dvar) 
    lm(as.formula(paste0(dvar, " ~ indus")),data=Boston)) 
+1

Аналогично, с 'переформулировать', вы можете сделать' fit <- lapply (myvars, function (dvar) lm (переформулировать («indus», dvar)), data = Boston)) '. – lmo

1

Вы можете также использовать dplyr & purrr подход, держать все в tibble, вытащить что вам нужно, когда вам это нужно. Нет никакой разницы в функциональности от методов lapply.

library(dplyr) 
library(purrr) 
library(MASS) 
library(stargazer) 

var_tibble <- tibble(vars = c("nox","crim"), data = list(Boston)) 

analysis <- var_tibble %>% 
    mutate(models = map2(data, vars, ~lm(as.formula(paste0(.y, " ~ indus")), data = .x))) %>% 
    mutate(tables = map2(models, vars, ~stargazer(.x, type = "text", dep.var.labels.include = FALSE, column.labels = .y))) 
0

Вы можете также использовать get():

# make a list of independent variables 
    list_x <- list("nox","crim") 

# create regression function 
    my_reg <- function(x) { lm(indus ~ get(x), data = Boston) } 

# run regression 
    results <- lapply(list_x, my_reg) 
Смежные вопросы