You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在ggplot的position_dodge2条形图中重排条形并添加Y轴网格线

问题解决:ggplot2条形图排序与Y轴网格线添加

需求说明

  1. 条形图排序要求:
    • 按funct_type类别整体降序排列(以该类别下最高频率值为排序依据)
    • 每个funct_type类别内,按SPP的frequency值降序排列
  2. 添加Y轴网格线,替代之前无效的尝试方法

解决方案代码

数据预处理与绘图完整代码

library(dplyr)
library(ggplot2)
library(forcats)

# 加载数据集
top32freq <- structure(list(identifier = c(1L, 2L, 5L, 6L, 17L, 7L, 4L, 11L, 20L, 24L, 8L, 18L, 22L, 10L, 15L, 3L, 9L, 13L, 23L, 34L, 14L, 12L, 16L, 42L, 43L, 30L, 38L, 29L, 33L, 28L, 27L), SPP = c("Penstemon", "Rosaceae Group 1", "Saxifraga OR Micranthes OR Boykinia", "Eriogonum", "Boykinia OR Saxifraga", "Vaccinium", "Hypericum", "Chamerion OR Epilobium OR Oenothera", "Aster Group 2", "Chrysosplenium tetrandum", "Oenothera", "Aster Group 1", "Poaceae", "Chamerion", "Luzula", "Abies", "Oxyria digyna", "Pinus", "Castilleja", "Erigeron", "Ribes", "Thalictrum", "Salix", "Xerophyllum tenax", "Valeriana", "Rhododendron", "Caryophyllaceae", "Sedum lanceolatum", "Senecio", "Polygonaceae", "Phrymaceae"), max = c(0.520063568, 0.479127183, 0.434079314, 0.362801825, 0.217608897, 0.191388889, 0.717687654, 0.120278432, 0.140414455, 0.078553735, 0.219305556, 0.437633588, 0.184346498, 0.383032052, 0.178396573, 0.503981446, 0.263381525, 0.358707915, 0.165725191, 0.046200125, 0.350292287, 0.644661654, 0.2640831, 0.016758773, 0.021521319, 0.039176109, 0.031850659, 0.202567022, 0.067327894, 0.20080737, 0.331692794), readsum = c(6.716942576, 5.503499137, 3.49976764, 2.309000619, 1.103758598, 1.913782497, 3.798417906, 1.263140584, 0.76553868, 0.574245876, 1.616440058, 0.866744904, 0.635800875, 1.478810665, 1.124030263, 3.881683753, 1.59921115, 1.247338241, 0.634873939, 0.234050052, 1.246069294, 1.262268812, 1.124014166, 0.097837052, 0.092817485, 0.344979525, 0.183615231, 0.353545529, 0.246583949, 0.386051108, 0.390301853), funct_type = c("Forb", "Forb", "Forb", "Forb", "Forb", "Shrub", "Forb", "Forb", "Forb", "Forb", "Forb", "Forb", "Graminoid", "Forb", "Graminoid", "Conifer", "Forb", "Conifer", "Forb", "Forb", "Shrub", "Forb", "Shrub", "Forb", "Forb", "Shrub", "Forb", "Forb", "Forb", "Forb", "Forb"), frequencyformula = c(52L, 50L, 47L, 47L, 47L, 46L, 45L, 45L, 45L, 44L, 43L, 43L, 42L, 41L, 41L, 40L, 40L, 37L, 37L, 36L, 30L, 29L, 29L, 27L, 27L, 25L, 23L, 22L, 22L, 20L, 18L), frequency = c(1, 0.961538462, 0.903846154, 0.903846154, 0.903846154, 0.884615385, 0.865384615, 0.865384615, 0.865384615, 0.846153846, 0.826923077, 0.826923077, 0.807692308, 0.788461538, 0.788461538, 0.769230769, 0.769230769, 0.711538462, 0.711538462, 0.692307692, 0.576923077, 0.557692308, 0.557692308, 0.519230769, 0.519230769, 0.480769231, 0.442307692, 0.423076923, 0.423076923, 0.384615385, 0.346153846)), class = "data.frame", row.names = c(NA, -31L))

# 数据预处理:设置因子排序
sorted_data <- top32freq %>%
  # 计算每个funct_type的最高frequency,用于类别排序
  group_by(funct_type) %>%
  mutate(type_max_freq = max(frequency)) %>%
  ungroup() %>%
  # 按funct_type的最高frequency降序,再按每个SPP的frequency降序设置因子水平
  mutate(
    funct_type = fct_reorder(funct_type, -type_max_freq),
    SPP = fct_reorder2(SPP, funct_type, -frequency)
  )

# 绘图
ggplot(sorted_data, aes(x = funct_type, y = frequency)) + 
  geom_bar(aes(fill = SPP), 
           position = position_dodge2(width = .9, preserve = "single"), 
           stat = "identity", color = "black") + 
  coord_cartesian(ylim = c(.3, 1)) + 
  ylab("Frequency across samples") + 
  xlab("functional plant types") + 
  ggtitle("Diet Frequency by Functional Type") + 
  scale_fill_viridis_d() +
  # 添加Y轴网格线
  theme_classic() +
  theme(
    axis.title = element_text(size = 16, face = "bold", family = "Caladea"), 
    strip.text.y = element_text(size = 18, face = "bold", family = "Caladea"), 
    plot.title = element_text(size = 28, face = "bold", family = "Caladea", hjust = 0.5), 
    axis.text = element_text(size = 18, face = "bold", family = "Caladea"),
    legend.position = "none",
    # 启用Y轴主网格线
    panel.grid.major.y = element_line(color = "grey92", size = 1, linetype = "solid"),
    # 可选:启用Y轴次网格线
    # panel.grid.minor.y = element_line(color = "grey95", size = 0.5, linetype = "dashed")
  )

关键说明

排序实现

  • 先通过group_by(funct_type)计算每个类别下的最高频率type_max_freq,以此作为funct_type的排序依据,用fct_reorder(funct_type, -type_max_freq)实现类别降序
  • 用fct_reorder2(SPP, funct_type, -frequency)确保每个funct_type内的SPP按自身frequency降序排列

Y轴网格线添加

  • theme_classic()默认隐藏网格线,需在theme()中显式设置panel.grid.major.y参数,指定线条颜色、粗细和线型;若需要次网格线,可添加panel.grid.minor.y参数
  • 避免使用非ggplot2原生的grids()函数,该函数不属于ggplot2语法体系

内容的提问来源于stack exchange,提问作者salix7

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.14 12:25:19