Reputation: 517
I'm writing a code that does long calculations over many time steps, and plots the results step by step.
This is R 3.6.1 under Windows 7, RStudio 1.1.383.
I'm working in RStudio, and trying to do the plots with ggplot2. The overall structure of the code is something like
for (step in 1:nb_steps){
... do big calculations
m<-ggplot(.... the data...) + ... some options
print(m)
}
You will note that I did assign the results of ggplot() to a variable, and I did explicitly print() it -- as suggested in many related posts, here as well as in RStudio web site.
In my (actual) example, the result is that the loop takes about 2-3 seconds for each iteration (the "big calculation" part). The (gg)graph is flashed for an instant, then disappear and the plot window blanks out -- as far as I can tell, shortly after the print() statement.
If I use a "regular" plot (in this case an image() )the code works as intended, i.e. the plot stays visible until it is over-plotted by something else.
Now my actual code is a bit long, so I tried to design a minimal reproducible example. This is what I came up with, for a result that is similar to the "main" example.
library(ggplot2)
data(mpg)
for(i in 1:10){
cat(i); cat("\n")
for (j in 1:100000){j*j} # Do something time-consuming
m<-ggplot(mpg, aes_(~ displ, ~ hwy, colour = ~trans)) +
geom_point() + ggtitle(paste("graph number",i))
print(m)
}
This gives the same result, i.e. the graph is briefly shown, then disappears, the window stays blank for a moment before the new graph comes in. It is a bit hard to keep an eye simultaneously on the console and the plot (!), but my impression is that the actual plot building (the ggplot() command) is somewhat time-consuming, and starts by blanking the window, then creates the plot, which is then drawn at the very end. Thus, I see a blank window for all the time it takes to run the ggplot() command itself. In my actual code, the ggplot() is more complex (it is a geom_raster() of a 50*50 matrix) so the delay is longer, so much in fact that I have more often a blank window than a plot !
Of course, I could add a Sys.sleep() at the end. I'd see the graph for a longer time, but the blank periods does not seem to decrease, and obviously this would make the run time longer, which is not what I want in the real-life case.
What I would like instead would be that the plot window should stay as it is until the print() statement. This would give the illusion of one plot replacing the previous one, without the interruption.
Any way of doing so ?
Thanks !
Upvotes: 3
Views: 3150
Reputation: 2368
For completeness, I will add the default, which is to use the base graphics. If there is not need for ggplot
graphics and the graphics are just being used for diagnostics, the base drawing package can whip out a graph very quickly. When I run MCMC, I will typically use base graphics for diagnostics, then ggplot2 for the fancy final stuff.
#base way
start <- Sys.time()
for(i in 1:10){
cat(i); cat("\n")
for (j in 1:100000){j*j} # Do something time-consuming
plot(mpg[["displ"]], mpg[["hwy"]], col = factor(mpg$trans),
main = paste("Graph Number", i))
legend("topleft", fill = factor(mpg$trans),legend = levels(factor(mpg$trans)),
ncol = 4)
}
end_time <- Sys.time()
end_time - start
It draws the graph and leaves it present for a while (and very quickly).
Upvotes: 0
Reputation: 448
One suggestion for you might be to save your ggplot object into a grob (grid graphical object) and then print the grob.
Doing it in this way - using your sample code on my laptop - shortens the time of blank periods by half.
library(ggplot2)
library(grid)
data(mpg)
for(i in 1:10){
cat(i); cat("\n")
for (j in 1:100000){j*j} # Do something time-consuming
m<-ggplot(mpg, aes_(~ displ, ~ hwy, colour = ~trans)) +
geom_point() + ggtitle(paste("graph number",i))
grid.draw(ggplotGrob(m))
}
Upvotes: 0