【问题标题】:Add percentage in the right side of the histogram with legend在带有图例的直方图右侧添加百分比
【发布时间】:2022-08-14 12:54:47
【问题描述】:

我有一个像这样的数据集(df):

Age n
18 2500
19 1200
20 4500
21 800
23 120
24 50
25+ 100

我创建了一个这样的代码 ggplot 按年龄显示学生身体

ggplot(df, aes(x=Age, y=n)) + 
      geom_bar(stat=\"identity\") + ggtitle(\"Student Body by Age at ETH in the assesment year\") + scale_y_continuous(labels = function(x) format(x, scientific = FALSE))

现在我想在直方图旁边创建一个图例,按年龄显示评估年份的成功率。有了这些数据集

Age % success
18-19 80
20-21 60
23-24 50
25+ 20

是否有代码可以在其中添加具有年龄成功率的图例?

直方图很好,但我想要一个图例,在右侧按年龄显示成功率。

    标签: r ggplot2


    【解决方案1】:

    您所描述的并不是 ggplot 意义上的真正传奇,但可以通过在图例通常所在的位置添加一个表格来实现。使用与@langtang 相同的数据名称,我们可以:

    library(ggpubr)
    library(patchwork)
    
    ggplot(df, aes(x=Age, y=n)) + 
      geom_bar(stat="identity") + 
      ggtitle("Student Body by Age at ETH in the assesment year") + 
      scale_y_continuous(labels = function(x) format(x, scientific = FALSE)) +
      ggtexttable(success_rates, rows = NULL, theme = ttheme("light")) +
      plot_layout(widths = 2:1)
    

    reprex package (v2.0.1) 于 2022 年 7 月 31 日创建

    【讨论】:

      【解决方案2】:

      您可以创建一个自定义图例(实际上是另一个 ggplot 图)并使用patchwork 添加两者,还可以进行一些自定义以使其良好。

      library(tidyverse)
      library(patchwork)
      
      df <- data.frame(
        Age = c(18, 19, 20, 21, 23, 24, 25),
        n = c(2500L, 1200L, 4500L, 800L, 120L, 50L, 100L)
      )
      
      pc_data <- data.frame(
        stringsAsFactors = FALSE,
        Age = c("18-19", "20-21", "23-24", "25+"),
        success = c(80, 60, 50, 20)
      )
      
      
      p1 <- ggplot(df, aes(x=Age, y=n)) + 
        geom_bar(stat="identity") +
        scale_y_continuous(labels = function(x) format(x, scientific = FALSE)) +
        scale_x_continuous(labels = 18:25, breaks = 18:25) +
        labs(y = NULL) +
        theme_bw() +
        theme(
          panel.grid.minor = element_blank(),
          panel.grid.major.x = element_blank()
        )
      
      p2 <- pc_data %>% 
        mutate(
          Age = fct_rev(factor(Age)),
          label_pos = success - (success/2)
        ) %>% 
        ggplot(aes(Age, success)) +
        geom_col(fill = colorspace::lighten("gray"), width = 0.7) +
        coord_flip() +
        labs( x = NULL, y = NULL, 
              title = "Success rate\nof Age") +
        geom_text(aes(Age, label_pos, label = paste0(success, "%")), 
                  size = 4) +
        theme_classic() +
        theme(
          axis.line = element_blank(),
          axis.text.y = element_text(size = 9, angle = 90, hjust = 0.5),
          axis.ticks = element_blank(),
          axis.text.x = element_blank(),
          plot.title = element_text(color = colorspace::lighten("black", amount = 0.5))
        )
      
      layout <- "
      AAAA##
      AAAABB
      "
      
      p1 + p2  + plot_layout(design = layout, heights = c(1, 30)) +
        plot_annotation(
          title = "Student Body by Age at ETH in the assesment year"
        )
      
      
      

      【讨论】:

      • 你的代码启发了我。你知道如何将数字放在左侧条形图的中间吗?
      • @JaimeGilmartin,您可以更改hjust 的值或更好的方法来做到这一点,创建一个将是条形长度一半的变量并将其用作geom_text 中的标签位置。我实际上已经基于此更新了我的答案,请参阅更新的代码。
      【解决方案3】:

      如果您愿意使用表格注释,则可以这样做,假设您的上述success_rates

      library(ggpp)
      success_legend = tibble(x=6,y=4000, success=list(success_rates))
      
      ggplot(df, aes(x=Age, y=n)) + 
        geom_bar(stat="identity") +
        ggtitle("Student Body by Age at ETH in the assesment year") +
        scale_y_continuous(labels = function(x) format(x, scientific = FALSE)) + 
        geom_table(data=success_legend, aes(x,y,label=success))
      

      输入:

      df = structure(list(Age = c("18", "19", "20", "21", "23", "24", "25+"
      ), n = c(2500L, 1200L, 4500L, 800L, 120L, 50L, 100L)), row.names = c(NA, 
      -7L), class = "data.frame")
      
      success_rates = structure(list(Age = c("18-19", "20-21", "23-24", "25+"), `% success` = c(80L, 
      60L, 50L, 20L)), row.names = c(NA, -4L), class = "data.frame")
      

      【讨论】:

        【解决方案4】:

        这是另一种选择:

        library(tidyverse)
        library(ggpubr)
        
        # make a ggplot chart
        p <- ggplot(df, aes(x=Age, y=n)) + 
          geom_bar(stat="identity") + 
          ggtitle("Student Body by Age at ETH in the assesment year") + 
          scale_y_continuous(labels = function(x) format(x, scientific = FALSE))
        
        
        # construct table    
        df_success <- ggtexttable(df_success, rows = NULL, 
                          theme = ttheme("lBlack"))
        
        grid.arrange(p,df_success, nrow = 1)
        
        

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2019-03-12
          • 2022-12-12
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2016-02-10
          相关资源
          最近更新 更多