仅按因子变量的一个级别对条形图进行排序

Posted

技术标签:

【中文标题】仅按因子变量的一个级别对条形图进行排序【英文标题】:Ordering a bar graph by only one level of a factor variable 【发布时间】:2020-04-27 18:52:40 【问题描述】:

我的数据如下所示:

Col1  Col2  Col3
A     Dog   3
A     Cat   5
A     Hat   6
B     Dog   8
B     Cat   3
B     Hat   4

Col1 和 Col2 是因子,A 是 Col1 的第一级。

我想将 Col2 绘制为按 Col3 降序排列的条形图,但 Col2 在 Col1 中定义为 A 的因子水平内的顺序优先。也就是说,我希望将数据绘制成如下图(我已经翻转了轴,以便 Col2 中的值位于 y 轴上,因此图表的条形将从上到下读取):

Col1  Col2  Col3
A     Hat   6
B     Hat   4
A     Cat   5
B     Cat   3
A     Dog   3
B     Dog   8

现在,我只能让 ggplot 显示由最大总体值 (8) 定义的条形,而不是仅在因子水平 A 内的最大值 (6)。所以它看起来像:

Col1  Col2  Col3
A     Dog   3
B     Dog   8
A     Hat   6
B     Hat   4
A     Cat   5
B     Cat   3

我知道我可以通过在 Col2 中重新指定因子的级别来手动执行此操作,但我的真实数据中有 40 个 Col2 值,因此需要大量输入。我已经使用arrange(Col1, desc(Col3)) %>% select(Col2) 对数据框进行了排序和削减,以获得一个包含正确排序 Col2 (right_order = "Hat", "Hat", "Cat", "Cat", "Dog", "Dog") 的向量,但我无法弄清楚如何使用该向量来告诉 ggplot 如何排列数据。我尝试在reorder 中使用它,但收到错误arguments must have the same length。我已经阅读了无数关于在 ggplot 中重新排序因子水平以进行绘图的问题和教程,但我找不到关于如何仅使用因子的一个水平内的顺序(Col1 中的 A)来排列图形的指导。

【问题讨论】:

【参考方案1】:

我们可以在使用自定义订单转换为factorarrange

library(dplyr)
df1 %>% 
    arrange(Col1, desc(Col3)) %>% 
    mutate(Col2 = factor(Col2, levels = unique(Col2))) %>% 
    arrange(Col2, Col1, desc(Col3))
#   Col1 Col2 Col3
#1    A  Hat    6
#2    B  Hat    4
#3    A  Cat    5
#4    B  Cat    3
#5    A  Dog    3
#6    B  Dog    8

数据

df1 <- structure(list(Col1 = c("A", "A", "A", "B", "B", "B"), Col2 = c("Dog", 
"Cat", "Hat", "Dog", "Cat", "Hat"), Col3 = c(3L, 5L, 6L, 8L, 
3L, 4L)), class = "data.frame", row.names = c(NA, -6L))

【讨论】:

我的数据有 160 个原始因子变量的值,在计算 Col3 的成对总和后,重新编码为 Col2 的 40 个级别(对 Col1 的每个级别重复)。因此,从原始数据中并不能立即看出 Col3 中的哪个值(以及 Col2 的水平)最终将是最大的。即使我可以在 Col1 的单个级别中检查 Col2 的 40 个级别的顺序,我也想避免手动重新排序 Col2 中因子的级别并使用正确顺序的向量(从排列(Col1,desc (Col3)) %>% select(Col2)) 代替。 @KellanBaker 这不是手动订购。我们首先根据'Col1'和Col3的降序排列,改变'Col2'的水平,然后再做arrange【参考方案2】:

您几乎已经有了答案(@akrun 也是如此),但我认为逐步进行是关键。通常,方法是相同的。首先,绘制您的数据 (df1):

ggplot(df1, aes(Col2, Col3)) + geom_col()

然后按照您的指定进行排列,注意输出是一个data.frame 对象,称为d。然后我们将该列 (d$Col2) 的 unique() 值映射到重构 d1$Col2

d <- df1 %>% arrange(Col1, desc(Col3)) %>% select(Col2)  # returns a dataframe!
df1$Col2 <- factor(df1$Col2, levels=unique(d$Col2))  # unique values of d$Col2 set to levels of df1$Col2 factor

然后您可以再次绘制并查看列重新排序:

我认为@akrun 方法的问题在于它无法在管道命令中进行分解。逐步进行:(1) 安排,(2) 从中获得独特的排序,(3) 重构。

【讨论】:

以上是关于仅按因子变量的一个级别对条形图进行排序的主要内容,如果未能解决你的问题,请参考以下文章

很想弄清楚 R 中的条形图上哪个因子级别已映射到哪个填充颜色?

带有ggplot2的发散堆积条形图:图例中的因子排序问题

R语言可视化包ggplot2绘制排序条形图实战:按照分类因子排序按照数值排序

根据ggplot中的两个条件对条形图进行排序

仅使用一个变量(无值或排名)对 ggplot2 条形图中的条形重新排序?

用条形图和点图来排序标签