This is an expanded version of the question I tried to ask last night - I thought I had it this morning, but it's still not working and I just do not understand what is going wrong. What I am trying to do is write a wrapper for lattice xyplot() that passes a whole bunch of its secondary arguments, so that I can produce similarly formatted graphs for several different data sets. This is what I've got: graph <- function (x, data, groups, xlab) { g <- eval(substitute(groups), data, parent.frame()) pg <- function(x, y, group.number, ...) { panel.xyplot(x, y, ..., group.number=group.number) panel.text(2, unique(y[x==2]), levels(g)[group.number], pos=4, cex=0.5) } xyplot(x, data=data, groups=substitute(g), type='l', ylab=list(cex=1.1, label='Mean RT (ms)'), xlab=list(cex=1.1, label=xlab), scales=list( x=list(alternating=c(1,1), tck=c(1,0)), y=list(alternating=c(1,0)) ), panel=panel.superpose, panel.groups=pg ) } "pg" is supposed to pick "g" up from the lexical enclosure. I have no idea whether that actually works, because it never gets that far. A typical call to this function looks like so:> graph(est ~ pro | hemi, sm, obs, "Probe type")(where 'sm' is a data frame that really does contain all four columns 'est', 'pro', 'hemi', and 'obs', pinky swear) and, as it stands above, invariably gives me this error: Error in eval(expr, envir, enclos) : object "est" not found I tried substitute(x) (as that seems to have cured a similar problem with "g") but then x is not a formula and method dispatch fails. Help? zw
I am not entirely happy with this solution but it does seem to work. In pg we pick groups out of its parent.frame and we place the entire body of graph2 in eval.parent(substitute(...)) pg <- function(x, y, subscripts, ..., group.number) { panel.xyplot(x, y, ...) panel.text(2, unique(y[x==2]), levels(parent.frame()$groups)[group.number], pos=4, cex=0.5) } graph2 <- function (x, data, groups, xlab) eval.parent(substitute({ xyplot(x, data=data, groups=groups, type='l', ylab=list(cex=1.1, label='Mean RT (ms)'), xlab=list(cex=1.1, label=xlab), scales=list( x=list(alternating=c(1,1), tck=c(1,0)), y=list(alternating=c(1,0)) ), panel=panel.superpose, panel.groups=pg) })) graph2(uptake ~ conc, CO2, Treatment, "X") On 6/8/07, Zack Weinberg <zackw at panix.com> wrote:> This is an expanded version of the question I tried to ask last night > - I thought I had it this morning, but it's still not working and I > just do not understand what is going wrong. > > What I am trying to do is write a wrapper for lattice xyplot() that > passes a whole bunch of its secondary arguments, so that I can produce > similarly formatted graphs for several different data sets. This is > what I've got: > > graph <- function (x, data, groups, xlab) { > g <- eval(substitute(groups), data, parent.frame()) > > pg <- function(x, y, group.number, ...) { > panel.xyplot(x, y, ..., group.number=group.number) > panel.text(2, unique(y[x==2]), > levels(g)[group.number], > pos=4, cex=0.5) > } > > xyplot(x, data=data, groups=substitute(g), > type='l', > ylab=list(cex=1.1, label='Mean RT (ms)'), > xlab=list(cex=1.1, label=xlab), > scales=list( > x=list(alternating=c(1,1), tck=c(1,0)), > y=list(alternating=c(1,0)) > ), > panel=panel.superpose, > panel.groups=pg > ) > } > > "pg" is supposed to pick "g" up from the lexical enclosure. I have no > idea whether that actually works, because it never gets that far. A > typical call to this function looks like so: > > > graph(est ~ pro | hemi, sm, obs, "Probe type") > > (where 'sm' is a data frame that really does contain all four columns > 'est', 'pro', 'hemi', and 'obs', pinky swear) and, as it stands above, > invariably gives me this error: > > Error in eval(expr, envir, enclos) : object "est" not found > > I tried substitute(x) (as that seems to have cured a similar problem > with "g") but then x is not a formula and method dispatch fails. > > Help? > zw > > ______________________________________________ > R-help at 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. >
On 6/8/07, Zack Weinberg <zackw at panix.com> wrote:> This is an expanded version of the question I tried to ask last night > - I thought I had it this morning, but it's still not working and I > just do not understand what is going wrong. > > What I am trying to do is write a wrapper for lattice xyplot() that > passes a whole bunch of its secondary arguments, so that I can produce > similarly formatted graphs for several different data sets. This is > what I've got: > > graph <- function (x, data, groups, xlab) { > g <- eval(substitute(groups), data, parent.frame()) > > pg <- function(x, y, group.number, ...) { > panel.xyplot(x, y, ..., group.number=group.number) > panel.text(2, unique(y[x==2]), > levels(g)[group.number], > pos=4, cex=0.5) > } > > xyplot(x, data=data, groups=substitute(g), > type='l', > ylab=list(cex=1.1, label='Mean RT (ms)'), > xlab=list(cex=1.1, label=xlab), > scales=list( > x=list(alternating=c(1,1), tck=c(1,0)), > y=list(alternating=c(1,0)) > ), > panel=panel.superpose, > panel.groups=pg > ) > } > > "pg" is supposed to pick "g" up from the lexical enclosure. I have no > idea whether that actually works, because it never gets that far. A > typical call to this function looks like so: > > > graph(est ~ pro | hemi, sm, obs, "Probe type") > > (where 'sm' is a data frame that really does contain all four columns > 'est', 'pro', 'hemi', and 'obs', pinky swear) and, as it stands above, > invariably gives me this error: > > Error in eval(expr, envir, enclos) : object "est" not found > > I tried substitute(x) (as that seems to have cured a similar problem > with "g") but then x is not a formula and method dispatch fails. > > Help? > zwIt's not lattice, but ggplot2, http://had.co.nz/ggplot2, is designed to make this easy because you don't have to specify the data set when creating the plot. e.g. install.packages("ggplot2", dep=T) library(ggplot2) # This is an abstract definition of a plot - it doesn't have any data yet p <- ggplot(mapping = aes(x=cyl, y=mpg)) + geom_point() + geom_smooth(method="lm") mt2 <- mtcars * 2 mt3 <- as.data.frame(mtcars ^ 2) # Add datasets p %+% mtcars p %+% mt2 p %+% mt3 # (the syntax isn't great, but you get the idea) # Or even changing the default mapping from data to visual properties p %+% mt3 + aes(x = mpg, y=wt) Obviously, you can do even more within a function, and the aes call is relatively easy to create programmatically (although not well documented currently, so please ask me for more details if you are interested). Hadley