ddply与lm()函数

jon*_*jon 15 r plyr dataframe

大家好我怎样才能将ddply函数用于线性模型:

x1 <- c(1:10, 1:10)
x2 <- c(1:5, 1:5, 1:5, 1:5)
x3 <- c(rep(1,5), rep(2,5), rep(1,5), rep(2,5))

set.seed(123)
y <- rnorm(20, 10, 3)
mydf <- data.frame(x1, x2, x3, y)

require(plyr)
ddply(mydf, mydf$x3, .fun = lm(mydf$y ~ mydf$X1 + mydf$x2)) 
Run Code Online (Sandbox Code Playgroud)

生成此错误:

model.frame.default中的错误(公式= mydf $ y~mydf $ X1 + mydf $ x2,drop.unused.levels = TRUE):变量'mydf $ X1'的类型(NULL)无效

感谢您的帮助.

Ram*_*ath 28

这是你需要做的.

mods = dlply(mydf, .(x3), lm, formula = y ~ x1 + x2)
Run Code Online (Sandbox Code Playgroud)

mods是包含回归结果的两个对象的列表.你可以从mods中提取你需要的东西.例如,如果你想提取系数,你可以写

coefs = ldply(mods, coef)
Run Code Online (Sandbox Code Playgroud)

这给了你

  x3 (Intercept)         x1 x2
1  1    11.71015 -0.3193146 NA
2  2    21.83969 -1.4677690 NA
Run Code Online (Sandbox Code Playgroud)

编辑.如果你愿意ANOVA,那么你就可以做到

ldply(mods, anova)

  x3 Df    Sum Sq   Mean Sq   F value     Pr(>F)
1  1  1  2.039237  2.039237 0.4450663 0.52345980
2  1  8 36.654982  4.581873        NA         NA
3  2  1 43.086916 43.086916 4.4273907 0.06849533
4  2  8 77.855187  9.731898        NA         NA
Run Code Online (Sandbox Code Playgroud)


JD *_*ong 12

拉姆纳特所解释的是完全正确的.但我会详细说明一下.

ddply期望一个数据帧,然后返回一个数据帧.该lm()函数将数据框作为输入,但返回一个线性模型对象.您可以通过查看lm的文档来查看?lm:

lm返回类"lm"的对象或类c的多个响应("mlm","lm").

因此,您不能只将lm对象推送到数据框中.您可以选择将输出强制lm转换为数据框,也可以将lm对象推送到列表而不是数据框中.

所以说明两个选项:

以下是将lm对象推送到列表中的方法(非常类似于Ramnath所说明的):

outlist <- dlply(mydf, "x3", function(df)  lm(y ~ x1 + x2, data=df))
Run Code Online (Sandbox Code Playgroud)

另一方面,如果你只想提取系数,你可以创建一个运行回归的函数,然后只返回数据框形式的系数,如下所示:

myLm <- function( formula, df ){
  lmList <- lm(formula, data=df)
  lmOut <- data.frame(t(lmList$coefficients))
  names(lmOut) <- c("intercept","x1coef","x2coef")
  return(lmOut)
}

outDf <- ddply(mydf, "x3", function(df)  myLm(y ~ x1 + x2, df))
Run Code Online (Sandbox Code Playgroud)