Hello,
at the Rgui command line I can easily remove a term from a fitted lm
object, like
fit <- lm(y~x1+x2+x3, data=myData)
update(fit,?.~.-x1)
However, I would like to do this in a function with term given as string, like
removeTerm <- function(linModel, termName) { ??? }
removeTerm(fit, "x1")
but I can not fill the ???. I already tried
removeTerm <- function(linModel, termName) { update(linModel,?.~. - termName
},
removeTerm <- function(linModel, termName) { update(linModel,?.~. -
as.name(termName)?},
removeTerm <- function(linModel, termName) { update(linModel,?.~. -
eval(termName)?},
removeTerm <- function(linModel, termName) { update(linModel,?.~. -
eval.parent(termName)?},
removeTerm <- function(linModel, termName) { update(linModel,?.~. -
get(termName)?},
but these attempts produce error messages.
Can you advise me here?
Kind regards,
Karsten
You need to review: ?update ?update.formula ?as.formula The way should be clear at that point. If not, then include a reproducible data example to work with. -- David On Nov 15, 2009, at 9:23 AM, Karsten Weinert wrote:> Hello, > at the Rgui command line I can easily remove a term from a fitted lm > object, like > > fit <- lm(y~x1+x2+x3, data=myData) > update(fit, .~.-x1) > > However, I would like to do this in a function with term given as > string, like > > removeTerm <- function(linModel, termName) { ??? } > removeTerm(fit, "x1") > > but I can not fill the ???. I already tried > > removeTerm <- function(linModel, termName) { update(linModel, .~. - > termName }, > removeTerm <- function(linModel, termName) { update(linModel, .~. - > as.name(termName) }, > removeTerm <- function(linModel, termName) { update(linModel, .~. - > eval(termName) }, > removeTerm <- function(linModel, termName) { update(linModel, .~. - > eval.parent(termName) }, > removeTerm <- function(linModel, termName) { update(linModel, .~. - > get(termName) }, > > but these attempts produce error messages. > > Can you advise me here? > > Kind regards, > Karsten-- David Winsemius, MD Heritage Laboratories West Hartford, CT
Hello David,
of course I read those help pages and searched the r-help archive.
I agree that the way should be clear, but I am stuck and looking for
help. Here is reproducible code
removeTerm1 <- function(linModel, termName) { update(linModel, .~. -
termName) }
removeTerm2 <- function(linModel, termName) { update(linModel, .~. -
as.name(termName)) }
removeTerm3 <- function(linModel, termName) { update(linModel, .~. -
eval(termName)) }
removeTerm4 <- function(linModel, termName) { update(linModel, .~. -
eval.parent(termName)) }
removeTerm5 <- function(linModel, termName) { update(linModel, .~. -
get(termName)) }
myData <- data.frame(x1=rnorm(10), x2=rnorm(10), x3=rnorm(10), y=rnorm(10))
fit <- lm(y~x1+x2+x3, data=myData)
# all this does not work, as I am expecting the function to return a
lm object with formula y~x2+x3
removeTerm1(fit, "x1")
removeTerm2(fit, "x1")
removeTerm3(fit, "x1")
removeTerm4(fit, "x1")
removeTerm5(fit, "x1")
Any help appreciated,
kind regards,
Karsten Weinert
2009/11/15 David Winsemius <dwinsemius at
comcast.net>:>
> You need to review:
>
> ?update
> ?update.formula
> ?as.formula
>
> The way should be clear at that point. If not, then include a reproducible
> data example to work with.
>
> --
> David
On 15/11/2009 9:23 AM, Karsten Weinert wrote:> Hello, > at the Rgui command line I can easily remove a term from a fitted lm > object, like > > fit <- lm(y~x1+x2+x3, data=myData) > update(fit, .~.-x1) > > However, I would like to do this in a function with term given as string, like > > removeTerm <- function(linModel, termName) { ??? } > removeTerm(fit, "x1") > > but I can not fill the ???. I already tried > > removeTerm <- function(linModel, termName) { update(linModel, .~. - termName }, > removeTerm <- function(linModel, termName) { update(linModel, .~. - > as.name(termName) }, > removeTerm <- function(linModel, termName) { update(linModel, .~. - > eval(termName) }, > removeTerm <- function(linModel, termName) { update(linModel, .~. - > eval.parent(termName) }, > removeTerm <- function(linModel, termName) { update(linModel, .~. - > get(termName) }, > > but these attempts produce error messages. > > Can you advise me here?There are two problems: 1. ".~." is different from ". ~ .". 2. You need to construct the formula ". ~ . - x1", and none of your expressions do that. You need to use substitute() or bquote() to edit a formula. For example, I think both of these should work: removeTerm <- function(linModel, termName) update(linModel, bquote(. ~ . - .(as.name(termName)))) removeTerm <- function(linModel, termName) update(linModel, substitute(. ~ . - x, list(x=as.name(termName)))) Duncan Murdoch
On Nov 15, 2009, at 11:15 AM, Karsten Weinert wrote:> Hello David, > > of course I read those help pages and searched the r-help archive.But did you look at the as.formula page?> > I agree that the way should be clear, but I am stuck and looking for > help. Here is reproducible codeAnd here is what seemed like the obvious extension of your example but using as.formula: myData <- data.frame(x1=rnorm(10), x2=rnorm(10), x3=rnorm(10), y=rnorm(10)) fit <- lm(y~x1+x2+x3, data=myData) remvterm <- function(ft, termname) update(ft, as.formula(paste(".~.-", termname, sep=""))) remvterm(fit, "x3") Call: lm(formula = y ~ x1 + x2, data = myData) Coefficients: (Intercept) x1 x2 -0.2598 -0.0290 -0.2645 -- David> removeTerm1 <- function(linModel, termName) { update(linModel, .~. - > termName) } > removeTerm2 <- function(linModel, termName) { update(linModel, .~. - > as.name(termName)) } > removeTerm3 <- function(linModel, termName) { update(linModel, .~. - > eval(termName)) } > removeTerm4 <- function(linModel, termName) { update(linModel, .~. - > eval.parent(termName)) } > removeTerm5 <- function(linModel, termName) { update(linModel, .~. - > get(termName)) } > > myData <- data.frame(x1=rnorm(10), x2=rnorm(10), x3=rnorm(10), > y=rnorm(10)) > fit <- lm(y~x1+x2+x3, data=myData) > > # all this does not work, as I am expecting the function to return a > lm object with formula y~x2+x3 > removeTerm1(fit, "x1") > removeTerm2(fit, "x1") > removeTerm3(fit, "x1") > removeTerm4(fit, "x1") > removeTerm5(fit, "x1") > > > Any help appreciated, > kind regards, > Karsten Weinert > > > > 2009/11/15 David Winsemius <dwinsemius at comcast.net>: >> >> You need to review: >> >> ?update >> ?update.formula >> ?as.formula >> >> The way should be clear at that point. If not, then include a >> reproducible >> data example to work with. >> >> -- >> David > > ______________________________________________ > R-help at r-project.org mailing list > https://stat.ethz.ch/mailman/listinfo/r-help > PLEASE do read the posting guide http://www.R-project.org/posting-guide.html > and provide commented, minimal, self-contained, reproducible code.David Winsemius, MD Heritage Laboratories West Hartford, CT
On 15/11/2009 11:28 AM, Duncan Murdoch wrote:> On 15/11/2009 9:23 AM, Karsten Weinert wrote: >> Hello, >> at the Rgui command line I can easily remove a term from a fitted lm >> object, like >> >> fit <- lm(y~x1+x2+x3, data=myData) >> update(fit, .~.-x1) >> >> However, I would like to do this in a function with term given as string, like >> >> removeTerm <- function(linModel, termName) { ??? } >> removeTerm(fit, "x1") >> >> but I can not fill the ???. I already tried >> >> removeTerm <- function(linModel, termName) { update(linModel, .~. - termName }, >> removeTerm <- function(linModel, termName) { update(linModel, .~. - >> as.name(termName) }, >> removeTerm <- function(linModel, termName) { update(linModel, .~. - >> eval(termName) }, >> removeTerm <- function(linModel, termName) { update(linModel, .~. - >> eval.parent(termName) }, >> removeTerm <- function(linModel, termName) { update(linModel, .~. - >> get(termName) }, >> >> but these attempts produce error messages. >> >> Can you advise me here? > > There are two problems: > > 1. ".~." is different from ". ~ .".Oops, wrong. Those are the same. Sorry... Duncan Murdoch> > 2. You need to construct the formula ". ~ . - x1", and none of your > expressions do that. You need to use substitute() or bquote() to edit a > formula. For example, I think both of these should work: > > removeTerm <- function(linModel, termName) > update(linModel, bquote(. ~ . - .(as.name(termName)))) > > > removeTerm <- function(linModel, termName) > update(linModel, substitute(. ~ . - x, list(x=as.name(termName)))) > > Duncan Murdoch > > ______________________________________________ > R-help at r-project.org mailing list > https://stat.ethz.ch/mailman/listinfo/r-help > PLEASE do read the posting guide http://www.R-project.org/posting-guide.html > and provide commented, minimal, self-contained, reproducible code.
Thanks Duncan and David
for opening my eyes :-). It took quite a while but I think I learned a
lot about lm today. I used your advice to produce "added variable
plots" as mentioned here [1], [2]. I would bet someone did it in R
already (may leverage.plot in car) but it was worth doing it myself.
Kind regards,
Karsten.
[1] http://www.minitab.com/support/documentation/answers/AVPlots.pdf
[2]
http://www.mathworks.com/access/helpdesk/help/toolbox/stats/addedvarplot.html
plotAddedVar.lm <- function(
linModel,
termName,
main="",
xlab=paste(termName, " | andere"),
ylab=paste(colnames(linModel$model)[1], " | andere"),
cex=0.7, ...) {
oldpar <- par(no.readonly = TRUE); on.exit(par(oldpar))
par(mar=c(3,4,0.4,0)+0.1, las=1, cex=cex)
yData = residuals(update(linModel, substitute(. ~ . - x,
list(x=as.name(termName)))))
xData = residuals(update(linModel, substitute(x ~ . - x,
list(x=as.name(termName)))))
plot(xData, yData, main=main, xlab="", ylab="")
mtext(side=2, text=ylab, line=3, las=0, cex=cex)
mtext(side=1, text=xlab, line=2, las=0, cex=cex)
abline(h=0)
abline(a=0, b=coefficients(linModel)[termName], col="blue")
}
plotAddedVar <- function(linModel,...) UseMethod("plotAddedVar")