【问题标题】:Grouped Frequency Bars in R using ggplot使用ggplot在R中分组频率条
【发布时间】:2017-04-28 10:24:52
【问题描述】:

我正在尝试生成一个包含多个组频率的条形图。我尝试使用 geom_bar() 但我一直遇到“错误:stat_count() 不能与 y 美学一起使用。”我为每个参与者设置了一行,包括年龄(2 个类别)、条件(2 个类别)和他们的表现(0 或 1)。根据我在手册和网上几乎所有地方阅读的内容,如果我使用

bar<-ggplot(data, aes(age, performance, fill = condition)) + geom_bar(position = "dodge")

我应该得到我想要的 (which is this),但我得到了错误,我无法弄清楚我错过了什么。 geom_bar() 不应该默认给出计数吗?当我使用 stat="identity" 时,我会得到像这样的完整条:how it actually looks。 请帮忙!任何建议将不胜感激。

编辑: 这是我的实际数据:

structure(list(ageyears = c(4L, 4L, 5L, 5L, 5L, 4L, 5L, 4L, 4L, 
4L, 4L, 4L, 4L, 4L, 4L, 4L, 4L, 4L, 5L, 4L, 5L, 4L, 5L, 4L, 5L, 
4L, 4L, 4L, 4L, 5L, 5L, 5L, 5L, 5L, 5L, 4L, 4L, 4L, 4L, 5L, 4L, 
5L, 5L, 4L, 4L, 4L, 5L, 4L, 4L, 5L, 4L, 5L, 4L, 4L, 5L, 5L, 4L, 
4L, 5L, 4L, 5L, 4L, 5L, 4L, 4L, 5L, 4L, 5L, 4L, 5L, 4L, 5L, 4L, 
4L, 4L, 4L, 4L, 4L, 4L, 5L, 4L, 4L, 5L, 5L, 4L, 5L, 5L, 4L, 4L, 
5L, 5L, 5L, 4L, 5L, 5L, 4L, 5L, 5L, 4L, 4L, 5L, 4L, 5L, 5L, 4L, 
5L, 4L, 4L, 5L, 5L, 4L, 5L, 5L, 5L, 4L, 5L, 4L, 5L, 4L, 5L, 4L, 
5L, 5L, 5L, 4L, 5L, 5L, 4L, 5L, 5L, 5L, 4L, 5L, 4L, 5L, 4L, 5L, 
4L, 5L, 4L, 5L, 4L, 5L, 4L, 5L, 4L, 5L, 4L, 5L, 4L, 5L, 5L, 5L, 
5L, 5L, 4L, 4L, 4L, 5L, 4L), MatrixLabels = structure(c(2L, 2L, 
1L, 1L, 2L, 2L, 1L, 1L, 1L, 1L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 2L, 
1L, 1L, 2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 2L, 2L, 
1L, 2L, 2L, 1L, 1L, 2L, 2L, 1L, 2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 
2L, 2L, 1L, 2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 2L, 
1L, 1L, 2L, 2L, 1L, 1L, 2L, 1L, 2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 
2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 
2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 
2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 
2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 2L, 2L, 1L, 1L, 
2L, 2L, 1L, 1L, 2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L, 2L), .Label = c("0", 
"1"), class = "factor"), Mat_sort_pass_fail = c(0L, 0L, 1L, 1L, 
0L, 0L, 1L, 0L, 1L, 1L, 1L, 0L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 0L, 
1L, 1L, 1L, 0L, 0L, 0L, 1L, 0L, 0L, 1L, 1L, 0L, 1L, 1L, 1L, 1L, 
0L, 0L, 0L, 1L, 0L, 1L, 1L, 0L, 1L, 1L, 0L, 0L, 0L, 0L, 1L, 0L, 
1L, 0L, 0L, 0L, 0L, 0L, 1L, 1L, 0L, 1L, 1L, 1L, 0L, 1L, 1L, 1L, 
1L, 1L, 1L, 1L, 1L, 1L, 0L, 0L, 0L, 1L, 0L, 1L, 0L, 0L, 0L, 0L, 
1L, 1L, 0L, 0L, 0L, 1L, 1L, 0L, 1L, 1L, 1L, 0L, 0L, 0L, 0L, 0L, 
0L, 0L, 1L, 0L, 0L, 1L, 1L, 1L, 0L, 0L, 0L, 0L, 1L, 0L, 1L, 1L, 
0L, 0L, 0L, 1L, 1L, 1L, 1L, 1L, 0L, 1L, 0L, 1L, 1L, 1L, 1L, 1L, 
1L, 1L, 1L, 0L, 1L, 1L, 1L, 0L, 1L, 0L, 0L, 0L, 0L, 0L, 1L, 0L, 
1L, 0L, 0L, 1L, 1L, 1L, 1L, 0L, 1L, 0L, 1L, 0L)), .Names = c("ageyears", 
"MatrixLabels", "Mat_sort_pass_fail"), row.names = c(1L, 2L, 
3L, 4L, 5L, 6L, 7L, 8L, 11L, 12L, 13L, 15L, 16L, 17L, 18L, 19L, 
20L, 21L, 23L, 24L, 25L, 26L, 27L, 28L, 29L, 30L, 31L, 32L, 33L, 
34L, 35L, 36L, 37L, 38L, 40L, 41L, 42L, 43L, 44L, 45L, 46L, 48L, 
49L, 50L, 51L, 52L, 53L, 54L, 55L, 56L, 57L, 58L, 60L, 61L, 62L, 
63L, 64L, 65L, 66L, 67L, 68L, 69L, 70L, 71L, 72L, 74L, 75L, 76L, 
77L, 78L, 79L, 80L, 82L, 83L, 85L, 86L, 87L, 88L, 89L, 90L, 91L, 
92L, 93L, 94L, 95L, 96L, 97L, 98L, 99L, 100L, 101L, 102L, 103L, 
104L, 105L, 106L, 107L, 108L, 109L, 110L, 111L, 112L, 113L, 114L, 
115L, 116L, 117L, 118L, 119L, 120L, 121L, 122L, 123L, 124L, 125L, 
126L, 127L, 128L, 129L, 130L, 131L, 132L, 133L, 134L, 135L, 136L, 
137L, 138L, 139L, 140L, 141L, 142L, 143L, 144L, 145L, 146L, 147L, 
148L, 149L, 150L, 151L, 152L, 153L, 154L, 155L, 156L, 157L, 158L, 
159L, 160L, 197L, 198L, 200L, 201L, 202L, 203L, 204L, 205L, 206L, 
207L), class = "data.frame")

【问题讨论】:

    标签: r ggplot2 graphing


    【解决方案1】:

    来自 geom_bar 的文档:

    默认情况下,geom_bar 使用 stat="count" 条形与每组病例数的比例(或者如果权重 提供了美学,重量的总和)。如果你想要高度 条形表示数据中的值,使用 stat="identity" 和 将变量映射到 y 美学。

    在你的情况下,你应该使用高度作为你的表现总和,因为你有一个汇总数据,所以 ggplot 应该使用stat = identity

    EDIT OP 粘贴 dput 后​​:

    您需要先汇总您的数据,我假设 df 是您的数据框,您可以使用任何东西进行汇总,我使用的是 data.table 和 baseR 聚合,您可以选择其中任何一个来完成如下:

    ###1. base R aggregate
    
     df <- aggregate(Mat_sort_pass_fail ~ ageyears + MatrixLabels, data=df1 ,sum)
    df$perc <- df$Mat_sort_pass_fail/sum(df$Mat_sort_pass_fail)
    names(df) <- c("age","condition","performance","percentage")
    
    
    
    ###2. sumarization using data.table
    library(data.table)
    
    dt <- setDT(df)
    dt1 <- dt[,list(Performance = sum(Mat_sort_pass_fail)),by=c("ageyears","MatrixLabels")]
    dt1[,perc:=Performance/sum(Performance)] ##percentage within column
    
    df <- data.frame(dt1)
    names(df) <- c("age","condition","performance","percentage")
    
    
    library(ggplot2)
    library(RColorBrewer)
    
    ggplot(df, aes(x = condition ,y=performance)) +
      geom_bar(aes(fill = factor(age)),stat="identity",position = "dodge") +
      ggtitle("Matrix Sort Performance") + 
      scale_fill_brewer(palette = "Dark2")
    
    ###In case you need the percentage run the below code:
    ggplot(df, aes(x = condition ,y=percentage)) +
      geom_bar(aes(fill = factor(age)),stat="identity",position = "dodge") +
      ggtitle("Matrix Sort Performance") + 
      scale_fill_brewer(palette = "Dark2")
    

    【讨论】:

    • 谢谢!因此,当我使用 stat=identity 时,我得到了一个奇怪的图表(我附加到原始问题的第二个链接)。当您说我的数据已汇总时,您是什么意思?我为每个参与者写了一行,我正在编辑问题以添加示例。
    • @GalPodjarny,您确定您的表现将始终为 0 和 1,因为在我看来,要获得理想的图表,它必须具有连续形式而不是二分形式。我认为当你总结你的表的条件和年龄时,你的表现应该总结在它的价值上,或者它可能只是计数,但它不能是一个二分形式。
    • 这个特定的变量是一个通过/失败变量,所以它是二分法的。我想要的图表取自用 excel 完成的相同数据,我只是希望在 R 中重新生成它,以便所有图表都能一致地完成。我没有总结任何数据,我给了 ggplot 数据框,如我的示例所示。知道为什么 ggplot 的行为方式如此吗? :)
    • @GalPodjarny ,你能在数据帧上做一个 dput , dput(df) 并将它粘贴到你的问题上吗?
    • @GalPodjarny,我添加了代码以防您需要百分比而不是总和
    【解决方案2】:

    通常它会根据您的数据计算频率。如果您的数据已经分组,请尝试以下操作:

    + geom_bar(stat="identity",position = "dodge")
    

    【讨论】:

      【解决方案3】:

      您可以使用geom_col() 作为geom_bar(stat = "identity") 的别名。

      你也有我认为错误的 aes 映射。

      我根据您发布的图表模仿了一些数据:

      df <- data.frame(age = factor(rep(4:5, each = 2), labels = c('4-Years-Olds', '5-Years-Olds')),
                       performance = c(48,37,65,65),
                       condition = factor(c(1,2,1,2), labels = c('No Label', 'Label')))
      
      library(ggplot2)
      
      ggplot(df) +
          geom_col(aes(condition, performance, fill = age), position = 'dodge') +
          scale_fill_manual(values = c('skyblue', 'darkolivegreen1'))
      

      【讨论】:

      • 谢谢!那么,我需要聚合数据吗?要创建一个得分为 1 的孩子数的表?因为这就是我在你的代码中看到的......我希望我能从向量中得到一个直接图?
      • 当然可以使用未汇总的数据,这正是我从您的问题中了解到的。与“dput(data)”共享您的数据以获得适当的答案
      猜你喜欢
      • 1970-01-01
      • 2021-11-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-12-17
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多