Save a plot as PNG and PDF only by one call to the

2020-07-24 04:30发布

问题:

I would like to have a plot in both pdf and png formats:

pdf("test.pdf")
plot(sin, -pi, 2*pi)
dev.off()

png("test.png")
plot(sin, -pi, 2*pi)
dev.off()

But, I am searching for a trick (preferably, not by loading a new package) in which plot function only be called once:

#no plot in pdf!
pdf("test1.pdf"); png("test1.png")
plot(sin, -pi, 2*pi)
dev.off(); dev.off()

Any suggestion would be appreciated.

回答1:

You can use dev.copy() for your purpose. For instance:

pdf("test.pdf")
a<-dev.cur()
png("test.png")
dev.control("enable")
plot(sin, -pi, 2*pi)
dev.copy(which=a)
dev.off()
dev.off()

You take note of the pdf device through dev.cur and then copy the plot from the png device to the pdf one.



回答2:

Not sure if this approach has any advantages over @nicolas answer and it technically does not answer your question, but it certainly demonstrates the perks of R's non-standard evaluation and solves your problem in a clean way:

save_plot <- function(p, file_name="test"){
  p <- substitute(p)
  pdf(paste0(file_name,".pdf"))
  eval(p)
  dev.off()

  png(paste0(file_name,".png"))
  eval(p)
  dev.off()

  eval(p) # if you don't also want to see your plot, change this to `invisible()`
}

save_plot(plot(sin, -pi, 2*pi))

In englisch: Write your own function that takes the unevaluated plot command as argument and simply evaluates it [=plots] once for each device.