在ggplot合并多数据集绘图后,如何保持因子类别顺序?
问题:强制维持ggplot中因子水平设定的类别顺序
我尝试将两个数据集和两种图表类型整合到单个ggplot中:主数据采用折线/连接点图展示(5个类别各包含2个同类观测值),第6个类别中的10个随机观测值使用geom_point()绘制散点图。但添加补充数据对应的第二个geom_point()后,通过因子水平指定的类别顺序无法维持,请问如何强制保持因子水平设定的类别顺序?
原始代码
main_data <- data.frame(variable = c(rep("min", 5), rep("max", 5)), category = c("apples", "bananas", "peaches", "pears", "melons"), value = c(seq(0.2, 0.28, by = 0.02), seq(0.8, 0.56, by = -0.06))) supplemental_data <- data.frame(variable = rep("random_observation", 10), category = rep("chicken", 10), value = runif(10, 0, 1)) all_data <- rbind(main_data, supplemental_data) %>% mutate(category = factor(category, levels = c("bananas", "peaches", "apples", "melons", "pears", "chicken"))) ggplot() + geom_line(data = all_data %>% filter(variable != "random_observation"), aes(x = category, y = value, group = variable, colour=variable), size = 1) + geom_point(data = all_data %>% filter(variable != "random_observation"), aes(x = category, y = value, group = variable, colour=variable)) + geom_point(data = all_data %>% filter(variable == "random_observation"), aes(x = category, y = value, group = variable), colour = "dark red") + scale_y_continuous(labels = scales::percent) + scale_colour_manual(values = c("Red", "Blue")) + theme(panel.background = element_rect(fill = "#C0C0C0", colour = "000000"), legend.position = "bottom")
解决方法
问题根源在于ggplot会根据每个图层传入的数据集自动推断离散x轴的刻度顺序。你第一个图层的数据集(过滤掉random_observation后)不包含chicken类别,导致ggplot自动调整了x轴顺序。
只需在代码中添加scale_x_discrete(limits = levels(all_data$category)),强制指定x轴刻度顺序为你预先设定的因子水平即可,无需修改其他逻辑。
修改后的完整代码
main_data <- data.frame(variable = c(rep("min", 5), rep("max", 5)), category = c("apples", "bananas", "peaches", "pears", "melons"), value = c(seq(0.2, 0.28, by = 0.02), seq(0.8, 0.56, by = -0.06))) supplemental_data <- data.frame(variable = rep("random_observation", 10), category = rep("chicken", 10), value = runif(10, 0, 1)) all_data <- rbind(main_data, supplemental_data) %>% mutate(category = factor(category, levels = c("bananas", "peaches", "apples", "melons", "pears", "chicken"))) ggplot() + geom_line(data = all_data %>% filter(variable != "random_observation"), aes(x = category, y = value, group = variable, colour=variable), size = 1) + geom_point(data = all_data %>% filter(variable != "random_observation"), aes(x = category, y = value, group = variable, colour=variable)) + geom_point(data = all_data %>% filter(variable == "random_observation"), aes(x = category, y = value, group = variable), colour = "dark red") + scale_y_continuous(labels = scales::percent) + scale_colour_manual(values = c("Red", "Blue")) + # 强制锁定x轴类别顺序为预设因子水平 scale_x_discrete(limits = levels(all_data$category)) + theme(panel.background = element_rect(fill = "#C0C0C0", colour = "000000"), legend.position = "bottom")
这个方法的核心是直接指定x轴的刻度范围和顺序,不受单个图层数据集的影响,确保始终遵循你设定的因子水平顺序。
内容的提问来源于stack exchange,提问作者quantyquanty
相关产品推荐
相关产品推荐

