【问题标题】:ggplot: add violin to a line graphggplot:将小提琴添加到折线图中
【发布时间】:2016-10-15 10:11:16
【问题描述】:

我正在 ggplot 中绘制折线图。每条线对应一个人及其随时间的发展。一个简化的、可重现的例子:

dat <- data.frame(x=rep(1:10, 10), y=rnorm(100), person=rep(LETTERS[1:10], each=10))
ggplot(dat, aes(x, y, group=person)) + geom_line(aes(color=person))

产生:

我想在 x = 11 处添加一把小提琴,以显示 y 轴上描绘的值的总体分布。

如果我在 ggplot 调用中添加+ geom_violin(),则会在每个 x 值处绘制小提琴(这是有道理的)。但我想要的是添加我用ggplot(dat, aes(x, y)) + geom_violin() 得到的小提琴。

如何将这两个geom_s 组合在一个图中以全面了解我的数据?


编辑:我让它与geom_errorbar 一起工作,但无法得到与小提琴类似的东西:

ggplot(dat, aes(x, y, group=person)) + geom_line(aes(color=person)) + 
  geom_errorbar(aes(x=11, ymax=mean(dat$y)+sd(dat$y), ymin=mean(dat$y)-sd(dat$y))) + 
  geom_point(aes(x=11, y=mean(dat$y)), size=4)

这给了我这个:

理想情况下,我希望使用小提琴而不是误差线来更好地反映分布。

【问题讨论】:

    标签: r ggplot2 data-visualization


    【解决方案1】:

    您需要在aesgeom_violin 中使用group = 1

    ggplot(dat, aes(x, y)) + 
      geom_line(aes(color = person)) + 
      geom_violin(aes(group = 1), fill = NA, size = 1.5) +
      theme_minimal()
    

    这给出了:

    要在线条图旁边绘制小提琴,您可以使用gridExtra 包中的grid.arrange

    p1 <- ggplot(dat, aes(x, y)) + 
      geom_line(aes(color = person)) + 
      theme_minimal(base_size = 14)
    p2 <- ggplot(dat, aes(x, y)) + 
      geom_violin(fill = NA) + 
      theme_minimal(base_size = 14) + 
      theme(axis.title = element_text(color = NA),
            axis.text = element_text(color = NA))
    
    library(gridExtra)
    grid.arrange(p1, p2, ncol=2, widths = c(4,1))
    

    给出:

    但是,线图和小提琴图现在被图例分开了。与:

    library(gtable)
    leg <- gtable_filter(ggplot_gtable(ggplot_build(p1)), "guide-box") 
    
    grid.arrange(p1 + guides(color = FALSE), p2, leg, ncol=3, widths = c(4,1,1))
    

    您可以再次将图例放置在图的最右侧:

    【讨论】:

    • 还有什么方法可以让我在 x = 11 处展示这把小提琴而不是跨越整个图表?理想情况下,我希望它显示在现在的线条和图例之间。
    【解决方案2】:

    我想通了:

    ggplot(dat, aes(x, y, group=person)) + geom_line(aes(color=person)) + 
      geom_violin(aes(x=rep(11, nrow(dat)), y=y, group=1))
    

    注意事项:在 geom_violin() 中设置 aes(x=11, y=y) 不起作用,因为 (a) x 和 y 必须具有相同的长度,并且 (b) 你会得到 10 把小提琴。

    (a) 可以通过rep()'ing 数字来创建与y 相等长度的向量来避免,(b) 可以通过设置group = 1 来避免(正如 Procrastinatus Maximus 的回答所指出的那样)。

    结果图:

    如果有更好的解决方案,我很乐意看到它!

    【讨论】:

    • 这不会给出正确的小提琴情节imo。另请参阅我的更新答案
    • “不正确”是什么意思?如果 x 轴上的值较大,小提琴可能会显示为一条垂直线,但可以使用 geom_violin(..., width=X) 进行调整 - 但小提琴 包含 y 中的数据。这有什么不正确的?
    • 这导致小提琴的形状不同
    • 但这不只是密度如何缩放的问题吗?使用的数据是一样的吧?
    • 但是小提琴只代表y值的分布。尝试(在我的代码中)将 11 替换为 4,然后是 5,然后是 6。它们都是相同的小提琴。在您最初的答案中(小提琴跨越了整个情节),所有不同的是width 参数(我认为)。
    猜你喜欢
    • 1970-01-01
    • 2023-02-22
    • 2021-09-29
    • 2020-11-07
    • 2018-12-16
    • 2021-10-07
    • 1970-01-01
    • 2017-10-11
    • 2019-07-07
    相关资源
    最近更新 更多