【问题标题】:R Stacked percentage bar plot with percentage of two factor variables with ggplotR堆叠百分比条形图,带有ggplot的两个因子变量的百分比
【发布时间】:2020-04-18 06:00:07
【问题描述】:

我正在尝试绘制两个因子变量并在图中用 % 标记结果。

我已经查看了这篇文章和他/她提供的链接:

How to center stacked percent barchart labels

您在这里看到的 ggplot 线实际上来自推荐的帖子之一:

sex <- c("F","F","M", "M", "M", "F","M","F","F", "M", "M", "M", "M","F","F", "M", "M", "F")
behavior <- c("A", "B", "C", "A", "B", "C", "A", "B", "C", "A", "B", "C", "A", "B", "C", "B", "C", "A")

BehSex <- data.frame(sex, behavior)

ggplot(BehSex, aes(x= factor(sex), fill= factor(behavior), y = (..count..)/sum(..count..)))+
  geom_bar() +
  stat_bin(geom = "text",
          aes(label = paste(round((..count..)/sum(..count..)*100), "%")),
          vjust = 5)

但是,当我使用该行时,我收到以下错误:

错误:StatBin 需要一个连续的 x 变量:x 变量是 离散的。也许你想要 stat="count"?

我尝试在 geom_bar() 中使用 stat="count",但它似乎没有按预期工作。

三个问题:
1)我做错了什么?
2) 我怎样才能设法绘制我想要的东西?
3)我如何绘制:%,然后在另一个图中计数?

这是我现在的情节

提前感谢您的帮助!

【问题讨论】:

    标签: r ggplot2 label bar-chart geom-bar


    【解决方案1】:

    这是另一种使用dplyr 准备数据的方法:

    编辑:添加计数。要显示其中一个,只需更改标签即可。

    library(dplyr)
    BehSexSum <- BehSex %>%
      count(sex, behavior) %>%
      mutate(pct = n / sum(n),
             pct_label = scales::percent(pct))
    
    ggplot(BehSexSum, aes(x= sex, fill = behavior, y = pct)) +
      geom_col() +
      geom_text(aes(label = paste(pct_label, n, sep = "\n")), 
                    lineheight = 0.8,
                    position = position_stack(vjust = 0.5)) +
      scale_y_continuous(labels = scales::percent)
    

    【讨论】:

    • 非常感谢乔恩!!不错的选择!
    【解决方案2】:

    关于您提到的帖子的答案,您必须使用position = position_stack() 显示百分比。

    此外,您可以使用 dplyr 包从数据框中获取百分比。在我看来,显示标签会更容易:

    library(dplyr)
    df <- BehSex %>% group_by(sex) %>% count(behavior) %>% mutate(Percent = n / sum(n)*100)
    
    # A tibble: 6 x 4
    # Groups:   sex [2]
      sex   behavior     n Percent
      <fct> <fct>    <int>   <dbl>
    1 F     A            2    25  
    2 F     B            3    37.5
    3 F     C            3    37.5
    4 M     A            4    40  
    5 M     B            3    30  
    6 M     C            3    30  
    

    然后,你可以像这样得到你的情节:

    ggplot(df, aes(x = sex, y = Percent, fill = behavior))+
      geom_bar(stat = "identity")+
      geom_text(aes(label = paste(Percent,"%"), y = Percent), 
                position = position_stack(vjust = 0.5))+
      coord_flip()+
      labs(x = "Sex", y = "Percentage",fill = "Behavior")
    

    【讨论】:

    • 太棒了!!!我已经经历了几个小时了。非常感谢 !但是,如果我错了,请纠正我,但我认为您提供的代码会覆盖函数 df。此外,因为我加载了很多包,我必须在调用 count() 之前指定 dplyr::。只是为读者提供一些精度。最后,它按预期工作。 BehSex2 % group_by(sex) %>% dplyr::count(behavior) %>% mutate(Percent = n / sum(n)*100)
    • df 将是一个新的数据框(当然,如果您的环境中已经有一个名为 df 的对象,它将被这个新的对象替换,但您可以根据需要命名它就像你对BehSex2 所做的那样)。如果在运行代码之前加载库dplyr,R 将使用dplyr 包中的count 函数。
    • @dc37 感谢您的精彩回答。赞成。如果可能,请告诉我如何切换轴(Y 轴的百分比和 x 轴的性别),因为我对数据使用了相同的代码并且我的 x 轴是年份。
    【解决方案3】:

    我认为将 y 轴标签格式化为百分比的更简单方法是使用scale_y_continuous(labels = scales::percent),而不是使用stat_bin(...)。因此,代码几乎可以保持不变。

    ggplot(BehSex, aes(x= factor(sex), fill= factor(behavior), y =(..count..)/sum(..count..)))+
      geom_bar() +
      #Set the y axis format as percentage
      scale_y_continuous(labels = scales::percent)+
      #Change the legend and axes names 
      labs(x = "Sex", y = "Percentage",fill = "Behavior")
    

    【讨论】:

    • 感谢乔纳森的回答!但是,如果我错了,请纠正我,但您的回答并不能解决标签问题(如何在图中绘制 % 标签)。也许我的问题不够清楚......我的错!
    • 是的,你是对的,呵呵。我忘了用标签解决问题。我觉得说的很清楚,但是忘记了。我的错!我认为@dc37 已经解决了这个问题。
    猜你喜欢
    • 2012-09-05
    • 2017-11-29
    • 2016-04-26
    • 1970-01-01
    • 1970-01-01
    • 2021-05-27
    • 1970-01-01
    • 2021-07-01
    • 1970-01-01
    相关资源
    最近更新 更多