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

如何将ggplot主Y轴设为对数刻度?双Y轴绘图报错求助

问题原因

你先后调用了scale_y_log10()和scale_y_continuous(),ggplot会自动用后一个Y轴刻度设置覆盖前一个,这就导致主Y轴的对数刻度被替换,同时触发"重复设置Y轴刻度"的报错。

修正代码
library(tidyr)
library(dplyr)
library(ggplot2)
library(scales)
theme_set(theme_bw())

# 处理0值(log10(0)无意义,替换为极小值避免报错)
df <- df %>% mutate(Secondary_conc = ifelse(Secondary_conc == 0, 1e-9, Secondary_conc))

ggplot(df) + 
  # 主Y轴柱状图(浓度,对数刻度)
  geom_bar(aes(x = reorder(Species, Species_order), y = Secondary_conc),
           stat = 'identity', fill = "cadetblue2") +
  # 整合主/次Y轴设置:主Y轴为对数刻度,次Y轴映射百分比
  scale_y_log10(
    name = expression(bold(Concentration~(ng/m^{3}))),
    breaks = trans_breaks("log10", function(x) 10^x),
    labels = trans_format("log10", math_format(10^.x)),
    sec.axis = sec_axis(
      trans = ~ . / 0.25,  # 主Y轴数值转百分比的反向转换
      name = "%",
      labels = function(x) round(x, 2)  # 优化百分比标签显示精度
    )
  ) + 
  # 次Y轴散点图(百分比需缩放匹配主Y轴范围)
  geom_point(aes(x = reorder(Species, Species_order), y = Secondary_perc * 0.25, color = "red")) + 
  theme(
    axis.title.y = element_text(face = "bold", size = 8),
    axis.text.x = element_text(face = "bold", size = 8, angle = -45, hjust = 0),
    legend.position = "none"
  ) + 
  labs(x = NULL)
关键修改说明
  1. 合并Y轴设置:将次Y轴的定义整合到scale_y_log10()的sec.axis参数中,避免重复设置Y轴导致覆盖。
  2. 调整缩放逻辑:散点的Y值从Secondary_perc/0.25改为Secondary_perc * 0.25,因为sec_axis的trans参数是从主Y轴数值转换到次Y轴数值的函数,需保证散点位置与次Y轴刻度对应。
  3. 处理0值问题:将浓度为0的数值替换为极小值(1e-9),避免log10(0)引发的绘图错误。
  4. 优化X轴标签:添加hjust=0让倾斜的物种名称更贴近坐标轴,提升可读性。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.04 15:08:20