在函数中创建lme对象

时间:2015-08-03 13:27:27

标签: r lm nlme

背景

我试图在一个基于某些参数的函数中拟合混合模型。如果我想使用contrast中的library(contrast),我必须使用变通方法,因为contrast使用call对象中的lme个广告位来确定data 1}},fixedrandom参数传递给函数中的lme(参见代码)。这与lm对象的情况并非如此。

数据

set.seed(1)
dat <- data.frame(x = runif(100), y1 = rnorm(100), y2 = rnorm(100),
                  grp = factor(sample(2, 100, replace = TRUE)))

代码

library(contrast)
library(nlme)
makeMixedModel1 <- function(resp, mdat = dat) {
   mF <- formula(paste(resp, "x", sep = "~"))
   mdat <- mdat[resp > 0, ]
   mod <- lme(mF, random = ~ 1 | grp, data = mdat)
   mC <- mod$call
   mC$fixed <- mF
   mC$data <- mdat
   mod$call <- mC
   mod
}

makeMixedModel2 <- function(resp, mdat = dat) {
   mF <- formula(paste(resp, "x", sep = "~"))
   mdat <- mdat[resp > 0, ]
   lme(mF, random = ~ 1 | grp, data = mdat)
}

mm1 <- makeMixedModel1("y1")
mm2 <- makeMixedModel2("y1")
contrast(mm1, list(x = 1)) ## works as expected
# lme model parameter contrast
# 
#   Contrast      S.E.      Lower     Upper    t df Pr(>|t|)
#  0.1613734 0.2169281 -0.2692255 0.5919722 0.74 96   0.4588

contrast(mm2, list(x = 1)) ## gives an error
# Error in eval(expr, envir, enclos) : object 'mF' not found

问题

我已将错误追踪到contrast评估fixed callmm2位内的mF广告符合makeMixedModel2等于makeMixedModel1的部分。当然在顶层不知道,因为它只在我的函数call中定义。 lm中的解决方法通过明确覆盖contrast中的相应位置来补救。

显然,对于mF个对象,这是以更智能的方式解决的,因为没有必要进行手动覆盖,因为mdat似乎在正确的上下文中评估了所有部分,当然{{ 1}}和makeLinearModel <- function(resp, mdat = dat) { mF <- formula(paste(resp, "x", sep = "~")) mdat <- mdat[resp > 0, ] lm(mF, data = mdat) } contrast(makeLinearModel("y1"), list(x = 1)) 也不知道:

lm

因此,我假设formuladataprint(mm1)的值存储在某处,以便也可以在不同的环境中检索。

我可以使用我的解决方法,但它有一些丑陋的副作用,因为contrast显示所有数据而不是简单的名称。所以我的问题是,是否有其他策略可以达到我想要的目的?或者我是否必须写信给lme的维护者并询问他,他是否可以更改call个对象的代码,使得hes不再依赖lm个插槽,而是尝试否则解决问题(正如# Setup sudo apt-key adv --keyserver keyserver.ubuntu.com --recv E56151BF DISTRO=$(lsb_release -is | tr '[:upper:]' '[:lower:]') CODENAME=$(lsb_release -cs) # Add the repository echo "deb http://repos.mesosphere.com/${DISTRO} ${CODENAME} main" | \ sudo tee /etc/apt/sources.list.d/mesosphere.list sudo apt-get -y update sudo apt-get -y install mesos 所做的那样)?

1 个答案:

答案 0 :(得分:1)

我认为你所打击的只是contrast() lme对象的错误实现。我会联系作者来解决它(这可能是最近因nlme而改变的结果)。但与此同时,您可以通过在contrast.lme()函数中而不是在模型构造函数中实现变通方法来避免副作用:

contrast.lme <- function(fit, ...) {
   mC <- fit$call
   mC$fixed <- formula(fit) 
   mC$data <- fit$data
   fit$call <- mC

   library(nlme)
   contrast:::contrastCalc(fit, ...)
}
assignInNamespace("contrast.lme", contrast.lme, "contrast")

mm2 <- makeMixedModel2("y1")

contrast(mm2, list(x = 1))

收率:

lme model parameter contrast

  Contrast      S.E.      Lower     Upper    t df Pr(>|t|)
 0.1613734 0.2169281 -0.2692255 0.5919722 0.74 96   0.4588

print(mm2)

收率:

Linear mixed-effects model fit by REML
  Data: mdat 
  Log-restricted-likelihood: -136.2472
  Fixed: mF 
(Intercept)           x 
 -0.1936347   0.3550081 

Random effects:
 Formula: ~1 | grp
        (Intercept)  Residual
StdDev:    0.131666 0.9365614

Number of Observations: 100
Number of Groups: 2