如何使用gratia绘制对数转换响应的GAM模型并指数化Y轴
解决方案
要实现用gratia的draw()绘制模型时将Y轴指数化,核心思路是利用draw()返回ggplot对象的特性,结合ggplot2的尺度转换功能来修改Y轴。
方法1:全局转换所有Y轴(适合仅关注拟合值的场景)
如果希望所有面板的Y轴都应用指数转换,直接在draw()返回的ggplot对象上添加scale_y_continuous():
library(mgcv) library(gratia) library(ggplot2) # 你的模型代码 gam.mod1 <- gam(log(sum7) ~ tap_type.fac + aq_race___1.factor + cityfac + aq_race___2.factor + aq_race___3.factor + aq_race___4.factor + aq_race___5.factor + aq_race___99.factor + s(aq_age), family = gaussian, data = d2.male) # 绘制模型并保存为ggplot对象 p <- draw(gam.mod1, residuals = TRUE) # 对Y轴应用指数转换,并重命名轴标签 p <- p + scale_y_continuous( trans = "exp", name = "sum7", guide = guide_axis(check.overlap = TRUE) # 避免标签重叠 ) + facet_wrap(~smooth, scales = "free_y") # 让每个面板Y轴独立缩放 # 显示图形 print(p)
方法2:仅转换拟合值面板的Y轴(残差面板保留原尺度)
残差是基于对数响应计算的,转换为指数尺度会失去诊断意义,因此可以针对性修改拟合值面板的Y轴:
# 绘制模型并保存为ggplot对象 p <- draw(gam.mod1, residuals = TRUE) # 遍历所有尺度,仅修改拟合值对应的Y轴 p$scales$scales <- lapply(p$scales$scales, function(scale) { if (scale$name == "log(sum7)") { scale$trans <- "exp" scale$name <- "sum7" } scale }) # 显示图形 print(p)
方法3:分开绘制效应图和残差图(更灵活)
如果需要更精细的控制,可以分别绘制效应图和残差图,再组合:
# 绘制拟合效应图(Y轴指数化) p_effects <- draw(gam.mod1) + scale_y_continuous(trans = "exp", name = "sum7") # 绘制残差诊断图(保留原尺度) p_residuals <- appraise(gam.mod1, type = "residuals") # 用patchwork组合图形(需先安装patchwork包) library(patchwork) p_effects / p_residuals
说明
trans = "exp"会自动将对数尺度的Y轴转换为原始尺度,对应你对sum7做的log()转换。- 残差图保留原尺度更符合模型诊断的逻辑,方法2和3是更推荐的选择。
内容的提问来源于stack exchange,提问作者Eazye
相关产品推荐
相关产品推荐

