【问题标题】:ggplot2: create ordered group bar plot - (use reorder)ggplot2:创建有序组条形图 - (使用重新排序)
【发布时间】:2016-08-27 11:16:13
【问题描述】:

我想在保持秩序的同时创建分组条形图。如果它是单列而不是分组条形图,则使用重新排序功能是显而易见的。但不确定如何在融化的 data.frame 上使用它。

下面是代码示例的详细解释:

假设我们有以下 data.frame:

d.nfl <- data.frame(Team1=c("Vikings", "Chicago", "GreenBay", "Detroit"), Win=c(20, 13, 9, 12))

在翻转时绘制一个简单的条形图。

ggplot(d.nfl, aes(x = Team1, y=Win)) + geom_bar(aes(fill=Team1), stat="identity") + coord_flip()

上面的情节没有订单,如果我想通过 win 来订购情节,我可以执行以下操作:

d.nfl$orderedTeam <- reorder(d.nfl$Team1, d.nfl$Win)
ggplot(d.nfl, aes(x = orderedTeam, y=Win)) + geom_bar(aes(fill=orderedTeam), stat="identity") + coord_flip()

现在假设我们添加另一列(到原始数据框)

d.nfl$points <- c(12, 3, 45, 5)

     Team1 Win points
1  Vikings  20     12
2  Chicago  13      3
3 GreenBay   9     45
4  Detroit  12      5

要生成分组条形图,首先我们需要将其融化:

library(reshape2)
> d.nfl.melt <- melt(d.nfl[,c('Team1','Win','points')],id.vars = 1)
> ggplot(d.nfl.melt,aes(x = Team1,y = value)) + geom_bar(aes(fill = variable),position = "dodge", stat="identity") + coord_flip()

ggplot 上面是无序的。

但是我如何做有序组条形图(升序方式)

【问题讨论】:

  • 您第一次对因子水平进行了重新排序,并且成功了。也许尝试在融化的数据框上设置因子级别顺序...?
  • 一些相关的here。使用堆叠,您只需要在绘图之前对数据集进行排序,但这似乎不适用于躲避。
  • @joran 试过没用:&gt; melted.theTable &lt;- within(d.nfl.melt, Team1 &lt;- factor(Team1, levels = names(sort(table(Team1), decreasing=FALSE)))) &gt; ggplot(melted.theTable,aes(x = Team1,y = value)) + geom_bar(aes(fill = variable),position = "dodge", stat="identity") + coord_flip()
  • 重新检查您设置级别顺序的尝试;这是错误的。

标签: r ggplot2 geom-bar


【解决方案1】:

这不是问题。

最简单的方法是不要在融化中丢弃你的有序团队:

d.nfl.melt <- melt(d.nfl,id.vars = c("Team1", "orderedTeam"))

或者,我们可以在熔化后使用reorder,并且只使用Win 元素来计算排序:

d.nfl.melt$ordered_after_melting = reorder(
    d.nfl.melt$Team1,
    X = d.nfl.melt$value * (d.nfl.melt$variable == "Win")
)

还有一个想法是从原始有序列中获取levels 并将它们应用到熔化因子:

d.nfl.melt$copied_levels = factor(
    d.nfl.melt$Team1,
    levels = levels(d.nfl$orderedTeam)
)

所有三种方法都给出相同的结果。 (我省略了 coord_flips,因为它们不会对问题添加任何内容,但您当然可以将它们重新添加。)

gridExtra::grid.arrange(
    ggplot(d.nfl.melt,aes(x = orderedTeam, y = value)) + 
        geom_bar(aes(fill = variable),position = "dodge", stat="identity"),
    ggplot(d.nfl.melt,aes(x = ordered_after_melting, y = value)) + 
        geom_bar(aes(fill = variable),position = "dodge", stat="identity"),
    ggplot(d.nfl.melt,aes(x = copied_levels, y = value)) + 
        geom_bar(aes(fill = variable),position = "dodge", stat="identity")
)

至于最简单的方法,我建议在熔化时只保留 orderedTeam 变量。您的代码似乎很难将其排除在外,保留它很容易。

【讨论】:

    【解决方案2】:

    您的问题提出的挑战是如何根据融合列中的子集值对因子 Team1 重新排序。

    @alistaire 和 @joran 对您的问题的 cmets 链接到很好的答案。 tl;dr 的答案是使用 levels() 将原始未熔化 data.frame 的排序应用到新的。

    library(reshape2)
    #Picking up from your example code:
    d.nfl.melt <- melt(d.nfl[,c('Team1','Win','points')],id.vars = 1)
    levels(d.nfl.melt$Team1)
    #Current order is alphabetical
    #[1] "Chicago"  "Detroit"  "GreenBay" "Vikings" 
    
    #Reorder based on Wins (using the same order from your earlier, unmelted data.frame)
    d.nfl.melt$Team1 <- factor(d.nfl.melt$Team1, levels = levels(d.nfl$orderedTeam)) #SOLUTION
    levels(d.nfl.melt$Team1)
    #New order is ascending by wins
    #[1] "GreenBay" "Detroit"  "Chicago"  "Vikings" 
    
    ggplot(d.nfl.melt,aes(x = Team1,y = value)) + 
      geom_bar(aes(fill = variable),position = "dodge", stat="identity") + coord_flip()
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-10-14
      • 1970-01-01
      • 1970-01-01
      • 2017-06-28
      • 2021-10-02
      相关资源
      最近更新 更多