Возврат графика из функции без его построения

Я хочу написать функцию, которая возвращает график, но не должна строить график. Он должен строить график только тогда, когда я попрошу его.

Вот МВЕ.

graph_functions <- function(x) {
  plot(1:length(x), x)
  points(1:length(x), x^2)
  t <- recordPlot()
  return(t)
}

answer <- graph_functions(1:10)

library(cowplot)
plot_grid(answer, answer)

В приведенном выше коде я не хочу, чтобы он строил график, когда я сначала вычисляю ответ, вызывая graph_functions(1:10). Я хочу, чтобы он строил график только тогда, когда я использую plot_grid().


person user2338823    schedule 01.12.2018    source источник


Ответы (2)


Вы можете открыть нулевое устройство и выполнить рендеринг на него. Обратите внимание, что если вы используете cowplot с графикой base-R, вам следует перейти на версию разработки с devtools::install_github("wilkelab/cowplot"). Он обеспечивает значительно улучшенную обработку графики base-R.

graph_functions <- function(x) {
  cur_dev <- grDevices::dev.cur()   # store current device
  pdf(NULL, width = 6, height = 6)  # open null device
  grDevices::dev.control("enable")  # turn on recording for the null device
  null_dev <- grDevices::dev.cur()  # store null device

  # make sure we always clean up properly, even if something causes an error
  on.exit({
    grDevices::dev.off(null_dev)
    if (cur_dev > 1) grDevices::dev.set(cur_dev) # only set cur device if not null device
  })

  # plot
  plot(1:length(x), x)
  points(1:length(x), x^2)
  recordPlot()
}

answer1 <- graph_functions(1:10)
answer2 <- graph_functions(1:20)
cowplot::plot_grid(answer1, answer2)

Создана 04 декабря 2018 г. с помощью пакета reprex (v0.2.1)

person Claus Wilke    schedule 04.12.2018

graph_functions<- function(x) {
  plot(1:length(x),x)
  points(1:length(x),x^2)
  t<- recordPlot()
  return(t)
}
answer <- c(1:10)
library(cowplot)
plot_grid(graph_functions(answer),graph_functions(answer))

Вы можете поместить функцию внутрь функции plot_grid() и просто сохранить параметры в переменной ответа.

person Jared C    schedule 01.12.2018
comment
Это был МВЕ. В моем коде graph_functions возвращает результаты с 3, 3 и 10 графиками в 3 разных заклинаниях. Мне нужно использовать plot_grid(plotlist = ..., nrow=2,ncol=2) для построения результатов. Возьмем, к примеру, случай, когда у меня вернулось 10 графиков. Я хочу отображать графики 4/4/2 на отдельных страницах. Я могу сделать plot_grid(graph_functions(answer)[1:4]),plot_grid(graph_functions(answer) [5:8]),plot_grid(graph_functions(answer)[9:10]), но каждое заклинание вызывает одну и ту же функцию 3 раза что неэффективно со временем, поскольку графики являются результатом интенсивной вычислительной регрессии. Есть ли другой способ? - person user2338823; 01.12.2018
comment
Может быть, ответ на этот вопрос и есть то, что вы ищете? stackoverflow.com/questions/23767645 / - person Jared C; 01.12.2018
comment
Вы хотите, чтобы я использовал ggplot с theme_base? Думаю, я должен это сделать. Гораздо проще вычислить график, а не отображать его в ggplot. - person user2338823; 01.12.2018
comment
конечно, ggplot был бы простым решением, но там есть ответ, в котором обсуждается, как удерживать обычные графики с помощью ?recordPlot - person Jared C; 01.12.2018
comment
@JaredC Я думаю, вопрос в том, как записать сюжет, чтобы сюжет не всплывал или не отображался в документе уценки. Я дал ответ, который делает это. stackoverflow.com/a/53623172/4975218 - person Claus Wilke; 06.12.2018