Nothing
## see Verbeek (2008), Section 3.2.3, p.64
petest <- function(formula1, formula2, data = list(), vcov. = NULL, ...)
{
## merge two models (if possible) and compute
## response y/log(y) and regressor matrices X and Z
## 1. If formulas are available: build big model first
if(inherits(formula1, "formula") && inherits(formula2, "formula")) {
ychar1 <- deparse(formula1[[2]])
ychar2 <- deparse(formula2[[2]])
if(nchar(ychar1) > nchar(ychar2)) {
if(substr(ychar1, 5, nchar(ychar1) - 1) != ychar2)
stop("formula1 does not seem to specify the transformed response of formula2")
trafo <- substr(ychar1, 1, 3)
if(!(trafo %in% c("log", "exp")))
stop("formula1 does not seem to specify the log/exp transformed response of formula2")
if(trafo == "log") {
islog1 <- TRUE
islog2 <- FALSE
} else {
islog1 <- FALSE
islog2 <- TRUE
}
formula <- formula1
if(length(formula) > 2) formula[[2]] <- NULL
formula[[2]] <- as.call(list(as.name("+"), as.name("."), formula[[2]]))
formula <- update(formula2, formula)
} else {
if(substr(ychar2, 5, nchar(ychar2) - 1) != ychar1)
stop("formula2 does not seem to specify the transformed response of formula1")
trafo <- substr(ychar2, 1, 3)
if(!(substr(ychar2, 1, 3) %in% c("log", "exp")))
stop("formula2 does not seem to specify the log/exp transformed response of formula1")
if(trafo == "log") {
islog1 <- FALSE
islog2 <- TRUE
} else {
islog1 <- TRUE
islog2 <- FALSE
}
formula <- formula2
if(length(formula) > 2) formula[[2]] <- NULL
formula[[2]] <- as.call(list(as.name("+"), as.name("."), formula[[2]]))
formula <- update(formula1, formula)
}
mf <- model.frame(formula, data = data)
yraw <- model.response(mf)
X <- model.matrix(delete.response(terms(formula1)), mf)
Z <- model.matrix(delete.response(terms(formula2)), mf)
m1 <- deparse(formula1)
m2 <- deparse(formula2)
if(trafo == "log") {
y <- if(islog1) log(yraw) else yraw
y2 <- if(islog2) log(yraw) else yraw
} else {
y <- if(islog1) yraw else exp(yraw)
y2 <- if(islog2) yraw else exp(yraw)
}
} else {
## 2. if not, go via row names
if(!inherits(formula1, "formula")) {
mf <- model.frame(formula1)
X <- if(is.matrix(formula1$x)) formula1$x else model.matrix(terms(formula1), mf)
y <- if(is.vector(formula1$y)) formula1$y else model.response(mf)
m1 <- deparse(formula(formula1))
} else {
mf <- model.frame(formula1, data = data)
y <- model.response(mf)
X <- model.matrix(formula1, data = data)
m1 <- deparse(formula1)
}
if(!inherits(formula2, "formula")) {
mf <- model.frame(formula2)
Z <- if(is.matrix(formula2$x)) formula2$x else model.matrix(terms(formula2), mf)
y2 <- if(is.vector(formula2$y)) formula2$y else model.response(mf)
m2 <- deparse(formula(formula2))
} else {
mf <- model.frame(formula2, data = data)
y2 <- model.response(mf)
Z <- model.matrix(formula2, data = data)
m2 <- deparse(formula2)
}
if(!(all(c(row.names(X) %in% row.names(Z), row.names(Z) %in% row.names(X))))) {
warning("models fitted on different subsets")
allnames <- row.names(X)[row.names(X) %in% row.names(Z)]
X <- X[allnames,]
Z <- Z[allnames,]
y <- y[allnames]
y2 <- y2[allnames]
}
if(isTRUE(all.equal(y2, log(y)))) {
islog1 <- FALSE
islog2 <- TRUE
} else if(isTRUE(all.equal(log(y2), y))) {
islog1 <- TRUE
islog2 <- FALSE
} else {
stop("response in formula2 does not seem to specify the log or exp of the response in formula1")
}
}
## for pretty printing
m1 <- paste(m1, collapse = "\n")
m2 <- paste(m2, collapse = "\n")
## check vcov.
if(!is.null(vcov.) && !is.function(vcov.)) stop("`vcov.' needs to be a function")
## fit auxiliary models:
y.hat1 <- lm.fit(X, y)$fitted.values
y.hat2 <- lm.fit(Z, y2)$fitted.values
y.aux1 <- if(islog1) y.hat2 - exp(y.hat1) else log(y.hat1) - y.hat2
y.aux2 <- if(islog2) y.hat1 - exp(y.hat2) else log(y.hat2) - y.hat1
aux1 <- cbind(X, y.aux1)
aux2 <- cbind(Z, y.aux2)
auxmod1 <- lm(y ~ 0 + aux1)
auxmod2 <- lm(y2 ~ 0 + aux2)
rval1 <- coeftest(auxmod1, vcov. = vcov., ...)
rval2 <- coeftest(auxmod2, vcov. = vcov., ...)
rval1 <- rval1[nrow(rval1), ]
rval2 <- rval2[nrow(rval2), ]
str1 <- paste("M1 +", if(islog1) "fit(M2)-exp(fit(M1))" else "log(fit(M1))-fit(M2)")
str2 <- paste("M2 +", if(islog2) "fit(M1)-exp(fit(M2))" else "log(fit(M2))-fit(M1)")
## put results together
title <- "PE test\n"
topnote <- paste("Model ", 1:2,": ", c(m1, m2), sep="", collapse="\n")
rval <- rbind(rval1, rval2)
rownames(rval) <- c(str1, str2)
rval <- structure(as.data.frame(rval), heading = c(title, topnote),
class = c("anova", "data.frame"))
return(rval)
}
Any scripts or data that you put into this service are public.
Add the following code to your website.
For more information on customizing the embed code, read Embedding Snippets.