如何在一个窗口上指定并排打印的数量 让我们考虑以下四个图: library(ggplot2) library(cowplot) set.seed(42) vec_1 <- rnorm(100) vec_2 <- runif(100) vec_3 <- rexp(100) vec_4 <- rpois(100,1) plot_1 <- ggplot()+aes(x=1:length(vec_1), y= vec_1) + geom_line() + xlab(NULL) + ylab('Norm') plot_2 <- ggplot()+aes(x=1:length(vec_2), y= vec_2) + geom_line() + xlab(NULL) + ylab('Unif') plot_3 <- ggplot()+aes(x=1:length(vec_3), y= vec_3) + geom_line() + xlab(NULL) + ylab('Exp') plot_4 <- ggplot()+aes(x=1:length(vec_4), y= vec_4) + geom_line() + xlab(NULL) + ylab('Poiss') plot_grids(plot_1, plot_2, plot_3, plot_4, plot_4, plot_4, ncol = 3L, nrow = 2L)

如何在一个窗口上指定并排打印的数量 让我们考虑以下四个图: library(ggplot2) library(cowplot) set.seed(42) vec_1 <- rnorm(100) vec_2 <- runif(100) vec_3 <- rexp(100) vec_4 <- rpois(100,1) plot_1 <- ggplot()+aes(x=1:length(vec_1), y= vec_1) + geom_line() + xlab(NULL) + ylab('Norm') plot_2 <- ggplot()+aes(x=1:length(vec_2), y= vec_2) + geom_line() + xlab(NULL) + ylab('Unif') plot_3 <- ggplot()+aes(x=1:length(vec_3), y= vec_3) + geom_line() + xlab(NULL) + ylab('Exp') plot_4 <- ggplot()+aes(x=1:length(vec_4), y= vec_4) + geom_line() + xlab(NULL) + ylab('Poiss') plot_grids(plot_1, plot_2, plot_3, plot_4, plot_4, plot_4, ncol = 3L, nrow = 2L),r,ggplot2,split,R,Ggplot2,Split,这是很容易做到的,但是-有没有可能一个命令就可以做到呢?例如,我试过 plot_grid(plot_1, plot_2, plot_3, plot_4, ncol = 2, nrow = 1), 但它只是截断了剩余的图。换句话说,我正在寻找一个解决方案,在这个解决方案中,我可以提供所有四个图,它将它们分成两个并排的图,其中包含两个图。我想要这样的解决方案,因为它可以简化我正在编写的复杂函数中的很多事情 关于facet_grid()函数 我试图使用它,但是如果我想得到与上面相同的结果(即,两个并

这是很容易做到的,但是-有没有可能一个命令就可以做到呢?例如,我试过

plot_grid(plot_1, plot_2, plot_3, plot_4, ncol = 2, nrow = 1),
但它只是截断了剩余的图。换句话说,我正在寻找一个解决方案,在这个解决方案中,我可以提供所有四个图,它将它们分成两个并排的图,其中包含两个图。我想要这样的解决方案,因为它可以简化我正在编写的复杂函数中的很多事情

关于facet_grid()函数

我试图使用它,但是如果我想得到与上面相同的结果(即,两个并排的两个图形的两倍),我使用:

我想获得两个图形,其中包含一行两列并排的绘图(就像我用
plot\u grid()
展示的那样),但是我得到了错误:
error:给定的尺寸不能容纳所有面板。请增加
ncol
nrow

编辑

我尝试对以下数据运行函数plot_grids():

library(ggplot2)
library(cowplot)
set.seed(42)
vec_1 <- rnorm(100)
vec_2 <- runif(100)
vec_3 <- rexp(100)
vec_4 <- rpois(100,1)


plot_1 <- ggplot()+aes(x=1:length(vec_1), y= vec_1) + geom_line() + xlab(NULL) + ylab('Norm')
plot_2 <- ggplot()+aes(x=1:length(vec_2), y= vec_2) + geom_line() + xlab(NULL) + ylab('Unif')
plot_3 <- ggplot()+aes(x=1:length(vec_3), y= vec_3) + geom_line() + xlab(NULL) + ylab('Exp')
plot_4 <- ggplot()+aes(x=1:length(vec_4), y= vec_4) + geom_line() + xlab(NULL) + ylab('Poiss')
plot_grids(plot_1, plot_2, plot_3, plot_4, plot_4, plot_4, ncol = 3L, nrow = 2L)
但我得到这些警告:

45: In as_grob.default(plot) : Cannot convert object of class list into a grob.
46: In as_grob.default(plot) : Cannot convert object of class waiver into a grob.
47: In as_grob.default(plot) : Cannot convert object of class list into a grob.
48: In as_grob.default(plot) :
  Cannot convert object of class ScalesListggprotogg into a grob.
49: In as_grob.default(plot) : Cannot convert object of class uneval into a grob.
50: In as_grob.default(plot) : Cannot convert object of class list into a grob.
编辑

现在我试图调整代码,使其与不正确的维数兼容,例如,如果我们有6个图要绘制,并且我们指定ncol=2和nrow=2,我想得到两个并排的图。第一个我想要四个图,第二个我想要剩下的两个。如果需要,我尝试添加空绘图:

plot_grids = function (plotlist = NULL, nrow, ncol) {
  plots_per_fig = nrow * ncol
  if (length(plotlist) %% plots_per_fig !=0) {
    df <- data.frame()
    for (i in 1:(length(plotlist) %% plots_per_fig)) {
      plotlist[[(length(plotlist)+i)]] <- ggplot(df)
    }
  }
  num_figs = length(plotlist) / plots_per_fig
  groups = if (num_figs == 1) list(plotlist)
  else unname(split(plotlist, cut(seq_along(plotlist), num_figs)))
  
  plot_grid_wrapper = function (plotlist) {
    do.call(
      cowplot::plot_grid,
      c(list(plotlist = plotlist, nrow = nrow, ncol = ncol))
    )
  }
  lapply(groups, plot_grid_wrapper)
}
仅给出部分正确的结果:

第一张图片:

第二幅图像:

如果第二张图片上有两个非空图形,而不是一个,一切都会很好。你知道为什么会这样吗

  • 将数据合并到表中:

    vecs = list(vec_1, vec_2, vec_3, vec_4)
    data = data.frame(
        x = unlist(lapply(lengths(vecs), seq)),
        y = unlist(vecs),
        dist = rep(c('normal', 'uniform', 'exponential', 'poisson'), times = lengths(vecs))
    )
    
  • 绘制它:

    ggplot(data) +
        aes(x = x, y = y) +
        geom_line() +
        facet_wrap(~ dist, ncol = 2L)
    
  • 如果您希望绘图只包含部分数据,请在将其传递到
    ggplot2
    之前对其进行过滤(我使用'dplyr'中的
    filter
    ,但任何方法都可以):

    要在侧面而不是顶部获得单独的y轴和标签,可以修改
    facet\u wrap
    调用,如下所示:

    facet_wrap(~ dist, ncol = 2L, strip.position = 'left', scales = 'free') +
    ylab('')
    
    要更改镶嵌条标签的外观,可以。要获得与屏幕截图几乎相同的外观,请使用

    theme(
        strip.background = element_rect(fill = 'white'),
        strip.placement = 'outside'
    )
    
  • 将数据合并到表中:

    vecs = list(vec_1, vec_2, vec_3, vec_4)
    data = data.frame(
        x = unlist(lapply(lengths(vecs), seq)),
        y = unlist(vecs),
        dist = rep(c('normal', 'uniform', 'exponential', 'poisson'), times = lengths(vecs))
    )
    
  • 绘制它:

    ggplot(data) +
        aes(x = x, y = y) +
        geom_line() +
        facet_wrap(~ dist, ncol = 2L)
    
  • 如果您希望绘图只包含部分数据,请在将其传递到
    ggplot2
    之前对其进行过滤(我使用'dplyr'中的
    filter
    ,但任何方法都可以):

    要在侧面而不是顶部获得单独的y轴和标签,可以修改
    facet\u wrap
    调用,如下所示:

    facet_wrap(~ dist, ncol = 2L, strip.position = 'left', scales = 'free') +
    ylab('')
    
    要更改镶嵌条标签的外观,可以。要获得与屏幕截图几乎相同的外观,请使用

    theme(
        strip.background = element_rect(fill = 'white'),
        strip.placement = 'outside'
    )
    

    plot\u grid
    始终生成单个绘图。您可以将其包装为一个简单的函数,以扩展它以生成多个绘图:

    #' Arrange plots into multiple grids
    #'
    #' \code{plot_grids} extends \code{\link[cowplot]{plot_grid}} by generating a list
    #' of multiple grids of plots.
    #'
    #' @param ... list of plots
    #' @param plotlist optional plots as a list
    #' @param nrow number of rows of plots per grid
    #' @param ncol number of colums of plots per grid
    #' @param plot_grid_args named vector of further arguments to pass to
    #'   \code{\link[cowplot]{plot_grid}}
    #' @return \code{plot_grids} returns a list of plots, each generated by
    #'   \code{\link[cowplot]{plot_grid}} with a subset of the plots passed via
    #'   \code{...} or \code{plotlist}.
    plot_grids = function (..., plotlist = NULL, nrow, ncol, plot_grid_args = NULL) {
        plots = c(list(...), plotlist)
        plots_per_fig = nrow * ncol
        num_figs = length(plots) / plots_per_fig
        groups = if (num_figs == 1L) list(plots)
            else unname(split(plots, cut(seq_along(plots), num_figs)))
    
        plot_grid_wrapper = function (plotlist) {
            do.call(
                cowplot::plot_grid,
                c(list(plotlist = plotlist, nrow = nrow, ncol = ncol), plot_grid_args)
            )
        }
        lapply(groups, plot_grid_wrapper)
    }
    
    然后呢,

    figs = plot_grids(plot_1, plot_2, plot_3, plot_4, ncol = 2L, nrow = 1L)
    

    plot\u grid
    始终生成单个绘图。您可以将其包装为一个简单的函数,以扩展它以生成多个绘图:

    #' Arrange plots into multiple grids
    #'
    #' \code{plot_grids} extends \code{\link[cowplot]{plot_grid}} by generating a list
    #' of multiple grids of plots.
    #'
    #' @param ... list of plots
    #' @param plotlist optional plots as a list
    #' @param nrow number of rows of plots per grid
    #' @param ncol number of colums of plots per grid
    #' @param plot_grid_args named vector of further arguments to pass to
    #'   \code{\link[cowplot]{plot_grid}}
    #' @return \code{plot_grids} returns a list of plots, each generated by
    #'   \code{\link[cowplot]{plot_grid}} with a subset of the plots passed via
    #'   \code{...} or \code{plotlist}.
    plot_grids = function (..., plotlist = NULL, nrow, ncol, plot_grid_args = NULL) {
        plots = c(list(...), plotlist)
        plots_per_fig = nrow * ncol
        num_figs = length(plots) / plots_per_fig
        groups = if (num_figs == 1L) list(plots)
            else unname(split(plots, cut(seq_along(plots), num_figs)))
    
        plot_grid_wrapper = function (plotlist) {
            do.call(
                cowplot::plot_grid,
                c(list(plotlist = plotlist, nrow = nrow, ncol = ncol), plot_grid_args)
            )
        }
        lapply(groups, plot_grid_wrapper)
    }
    
    然后呢,

    figs = plot_grids(plot_1, plot_2, plot_3, plot_4, ncol = 2L, nrow = 1L)
    


    谢谢你的回答,康拉德,但是你的代码将所有四个图都绘制在一起,这并不是我想要的。有关更多详细信息,请查看我更新的问题。@John我真的不明白问题所在:我的代码生成的排列与您的屏幕截图中的完全相同。唯一的区别是绘图的顺序,可以通过将
    dist
    设置为有序因子来指定。不完全相同-您有一个绘图包含四个绘图,我有两个绘图包含两个绘图;)@约翰:好的,从截图上看不到但是好的,这很容易实现,只需在将数据传递到
    ggplot
    之前过滤数据。请参阅更新的答案。是的,您是对的,我更改了一点屏幕截图的外观以使其更可见;))在将数据传递给ggplot之前,您能告诉我过滤数据的确切含义吗?我不知道这对我的问题有什么帮助。谢谢你的回答,康拉德,但是你的代码将所有四个图都绘制在一起,这并不是我想要的。有关更多详细信息,请查看我更新的问题。@John我真的不明白问题所在:我的代码生成的排列与您的屏幕截图中的完全相同。唯一的区别是绘图的顺序,可以通过将
    dist
    设置为有序因子来指定。不完全相同-您有一个绘图包含四个绘图,我有两个绘图包含两个绘图;)@约翰:好的,从截图上看不到但是好的,这很容易实现,只需在将数据传递到
    ggplot
    之前过滤数据。请参阅更新的答案。是的,您是对的,我更改了一点屏幕截图的外观以使其更可见;))在将数据传递给ggplot之前,您能告诉我过滤数据的确切含义吗?我不确定它对我的问题有什么帮助。这个函数基本上已经存在于patchwork::wrap_plots中,它以ggplot对象为对象list@tjebo
    wrap_plots
    是否生成绘图列表?据我所知,它总是生成单个绘图,示例为
    plot\u grid
    。这就是说,对“拼凑”的呼喊是好的:我相信它本质上取代了“cowplot”来安排情节。但我并没有真正使用这两种方法,所以我不是专家。你是对的,对不起,我认为我误解了OP,然后也误读了你的函数:)我个人更喜欢拼凑,但cowplot有它的优点。这是一个相当好的代码,但为什么如果我有ncol=2,nrow=2,我会看到错误无效的间隔数?我想它应该把所有的东西都画在一个图上,对吗?@John是的,我没有解释那个案例,因为这样你就可以调用
    plot\u grid
    ,对吗?现在已修复。该函数基本上已存在