如何在 ggplot2 条形图中使用一个变量实现连续填充

3

我正在使用 ggplot2movies 库来处理我的数据 movies

请注意,我提到的 MPAA 分级和用户评分是两个不同的概念。如果您不想加载 ggplot2movies 库,这里提供了相关数据的示例:

> head(subset(movies[,c(5,17)], movies$mpaa!=""))
# A tibble: 6 x 2
  rating mpaa 
   <dbl> <chr>
1    5.3 R    
2    7.1 PG-13
3    7.2 PG-13
4    4.9 R    
5    4.8 PG-13
6    6.7 PG-13

这里我制作了一个条形图,显示具有任何mpaa评级的电影频率:

ggplot(data=subset(movies, movies$mpaa!=""), aes(mpaa)) +
  geom_bar()

enter image description here

现在我想根据IMDB用户评分来填充条形图的颜色。 我不想使用factor(rating),因为评分列中有大量不同的值。 然而,当我尝试像将连续填充颜色分配给geom_bar一样使用连续填充时,我得到了相同的图形。

ggplot(data=subset(movies, movies$mpaa!=""), aes(mpaa, fill=rating)) +
  geom_bar()+ 
  scale_fill_continuous(low="blue", high="red")

我认为这与我的条形图基于单个变量的频率有关,而不是带有计数列的数据框。我可以创建一个新的包含mpaa类别及其计数的数据框,但我更想知道如何使用原始的movies数据集和单个ggplot来制作此图。
编辑:使用aes(mpaa,group=rating,fill=rating)会得到一个几乎正确的图表,只是条形和图例被交换了。enter image description here

我的意思是我不想使用因素,我想要一个连续的刻度。因此,每个条将是从蓝色到红色的渐变,红色表示更高的用户评级。我猜我可以切成离散的组,但这仍然会给出离散的填充,而不是连续的填充。 - Jared C
你可以尝试使用 aes(mpaa, group = rating, fill = rating) - hrbrmstr
这可能有效,也可能无效。现在的条形图是渐变的,但是条形和刻度已经交换了位置。https://i.imgur.com/0qlXOQq.png - Jared C
2个回答

2
您可以使用以下代码反转图例:+ guides(fill=guide_colourbar(reverse=TRUE)),但是颜色渐变似乎不太具有信息性。另一个选择是将rating分为离散范围,如下面的示例所示,这提供了对每个mpaa类别内评级分布的更清晰指示。然而,由于不同的条形高度,平均评级或评级分布因mpaa类别而异并不清楚。
library(tidyverse)
library(ggplot2movies)
theme_set(theme_classic())

movies %>% 
  filter(mpaa != "") %>% 
  mutate(rating = fct_rev(cut(rating, seq(0,ceiling(max(rating)),2)))) %>% 
  ggplot(aes(mpaa, fill=rating)) +
    geom_bar(colour="white", size=0.2) + 
    scale_fill_manual(values=c(hcl(240,100,c(30,70)), "yellow", hcl(0,100,c(70,30))))

在这里输入图片描述

也许箱线图或小提琴图会更加有用。在下面的箱线图示例中,由于varwidth=TRUE参数,箱子的宽度与评分电影数量的平方根成比例(我不是很喜欢这个方法,因为平方根转换很难解释,但我认为将其作为一种选择)。在小提琴图中,每个小提琴的面积与每个mpaa类别中的电影数量成比例(由于scale="count"参数)。我还在x轴标签中放置了每个类别中电影的数量,并用蓝色标记了每个mpaa类别的平均评分。

p = movies %>% 
  filter(mpaa != "") %>% 
  group_by(mpaa) %>% 
  mutate(xlab = paste0(mpaa, "\n(", format(n(), big.mark=","), ")")) %>% 
  ggplot(aes(xlab, rating)) +
    labs(x="MPAA Rating\n(number of movies)", 
         y="Viewer Rating") +
    scale_y_continuous(limits=c(0,10))

pl = list(geom_boxplot(varwidth=TRUE, colour="grey70"),
          geom_violin(colour="grey70", scale="count",
                      draw_quantiles=c(0.25,0.5,0.75)),
          stat_summary(fun.y=mean, geom="text", aes(label=sprintf("%1.1f", ..y..)), 
                         colour="blue", size=3.5))  

gridExtra::grid.arrange(p + pl[-2], p + pl[-1], ncol=2)

enter image description here


2
我同意并且甚至会认为梯度根本没有增加任何信息价值。 - hrbrmstr
确实,梯度并没有提供太多信息价值。然而,如果组的大小相似且评分分布更加多样化,连续填充可能会提供一些有趣的结果。我仍在学习R语言,因此知道如何做这个对我很有帮助,无论它最终是否成为一个有用的可视化工具。此外,这个答案还提供了一些更有用的替代方案。 - Jared C

0

我不确定下面是不是你想要的。
当按照 rating 进行着色时,默认的 stat = "count" 无法工作,因此我对数据进行了转换。

library(ggplot2movies)
library(dplyr)

data("movies")

subset(movies, mpaa != "") %>%
  group_by(mpaa) %>%
  summarise(rating = sum(rating)) %>%
  ggplot(aes(x = mpaa, y = rating, fill = rating)) +
  geom_bar(stat = "identity") +
  scale_fill_continuous(low="blue", high="red")

enter image description here


不,如果你将评分相加,那么显然拥有更多值的类别将具有更高的最终值。使用评分的平均值会给出你想要的答案,但是https://i.imgur.com/0qlXOQq.png更符合我的想法。然而,在这个例子中,条形图和图例被交换了,所以我不确定它是否正确。 - Jared C

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接