On Fri, 2007-01-26 at 11:50 -0500, Michael Rennie wrote: > Hi, there > > I'm trying to plot what is returned from a call to tapply, and can't figure > out how to do it. My guess is that it has something to do with the > inclusion of row names when you ask for the values you're interested in, > but if anyone has any ideas on how to get it to work, that would be > stellar. Here's some example code: > > y1<-rnorm(40, 2) > x1<-rep(1:2, each=20) > x2<-rep(1:2, each=10 times=2) > > ex.dat<-data.frame(cbind(y1,x1,x2)) > > ex.dat$x1<-factor(ex.dat$x1, labels=c("A", "B")) > ex.dat$x2<-factor(ex.dat$x2, labels=c("C", "D")) > > attach(ex.dat) > > xbar<-tapply(ex.dat$y1, ex.dat[,-1], mean) > xbar > > #values I'd like to plot: > row.names(xbar) #levels of x1 > xbar[,1] #mean response of y1 for group C (x2) across x1 > > #plot mean response y1 for group C against x1 (i.e., using x2 as a grouping > factor). > plot(row.names(xbar), xbar[,1], ylim=range[y1]) > > #This is where things break down. The error message states that I need > "finite xlim values" but I haven't assigned anything to xlim. If I just > plot the data: > > plot(x1, y1) > > #This works fine. > > #And, I can get this to work: > > stripchart(xbar[1,]~row.names(xbar), vert=T) > > #However, I'd like to then add the values for the second set of means > (i.e., mean values for group D against x1, or (xbar[,2])) to the plot. > #I tried following up the previous command with: > > points(row.names(xbar), xbar[,2]) > > #But that returns an error as well (NAs introduced by coercion). > > > > Any suggestions? > > Cheers, > > Mike > > PS- some of you might suggest for me to use interaction.plot, since this is > essentially what I'm building here. True, but I can't get error bars using > interaction.plot. I'm therefore trying to build my own version where I can > specify the inclusion of error bars. Presumably the interaction.plot has > figured out how to do what I'm attempting, so I have some faith that I am > on the right track....
Michael, The problem is that when you are using the rownames for 'xbar', they are a character vector: > str(rownames(xbar)) chr [1:2] "A" "B When you attempt to use the same values from 'ex.dat$x1', they are factors, which are being coerced to their numeric equivalents, so that they can work as x axis values. > str(ex.dat$x1) Factor w/ 2 levels "A","B": 1 1 1 1 1 1 1 1 1 1 ... > as.numeric(ex.dat$x1) [1] 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 2 2 2 2 2 2 2 2 2 2 2 2 2 2 [35] 2 2 2 2 2 2 I might note using the following: par(mfcol = c(1, 3)) with(ex.dat, plot(1:2, xbar[, 1], ylim = range(y1), type = "b", col = "red", lty = c("dashed", "solid"), xaxt = "n", xlab = "x1", ylab = "mean of y1")) with(ex.dat, points(1:2, xbar[, 2], col = "blue", type = "b")) axis(1, at = 1:2, labels = c("A", "B")) matplot(1:2, xbar, col = c("red", "blue"), pch = 21, type = "b", ylim = range(y1), lty = c("dashed", "solid"), xaxt = "n", xlab = "x1", ylab = "mean of y1") axis(1, at = 1:2, labels = c("A", "B")) with(ex.dat, interaction.plot(x1, x2, response = y1, type = "b", pch = 21, col = c("red", "blue"), ylim = range(ex.dat$y1), legend = FALSE)) You get basically the same 3 plots, with the principal difference in interaction.plot() being a different x axis range. Using interaction.plot(), you can get the proper basic plot and then add the CI's if you wish, since you know the x axis values of the mean estimates, which is 1:NumberOfGroups (as in a boxplot). interaction.plot() actually uses matplot() internally. HTH, Marc Schwartz ______________________________________________ R-help@stat.math.ethz.ch 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.