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

如何在brms中为广义可加模型平滑变量s()设置固定与随机效应先验?

问题描述

如何在brms的set_prior命令中,为brms集成的广义可加模型(GAM)的固定效应和随机效应部分中的平滑变量s()设置先验?具体来说,需要为平滑变量sDev_Yr_1设置非平坦先验,同时要考虑该变量随Dev_Yr取值范围变化的情况,该如何定义这个单一平滑变量的先验?

所用模型代码
Model_GAM <- brm(
  bf(Trended_Incr_PP_Def ~ Dev_Yr_1_Factor + s(Dev_Yr, k=3, m=2) + Cal_Yr_Time,
     sigma ~ 0 + Intercept + Dev_Yr_6_Cap + Dev_Yr_10_Spline ),
  iter = 4000,
  prior = GAM_prior,
  seed = 8603529,
  control = list(adapt_delta = .99 ),
  data = Train_Triangle_All_Operation, 
  family = lognormal()
)
模型摘要输出
summary(Model_GAM)
Family: lognormal
Links: mu = identity; sigma = log
Formula: Trended_Incr_PP_Def ~ Dev_Yr_1_Factor + s(Dev_Yr, k = 3, m = 2) + Cal_Yr_Time
sigma ~ 0 + Intercept + Dev_Yr_6_Cap + Dev_Yr_10_Spline
数据:Train_Triangle_All_Operation(观测数:253)
抽样:4条链,每条链iter=4000;warmup=2000;thin=1;
热身完成后总抽样数:8000

平滑项:
          Estimate Est.Error l-95% CI u-95% CI Rhat Bulk_ESS Tail_ESS
sds(sDev_Yr_1)    14.27      6.99     6.67    32.76 1.00     3983     4393

总体水平效应:
                      Estimate Est.Error l-95% CI u-95% CI Rhat Bulk_ESS Tail_ESS
Intercept                 -0.77      0.27    -1.30    -0.24 1.00     7033     5186
Dev_Yr_1_Factor2           5.10      0.28     4.57     5.66 1.00     6507     4634
Cal_Yr_Time                0.01      0.00     0.00     0.02 1.00     8006     4830
sigma_Intercept            0.53      0.09     0.35     0.71 1.00     4214     4553
sigma_Dev_Yr_6_Cap        -0.33      0.03    -0.38    -0.27 1.00     4068     4369
sigma_Dev_Yr_10_Spline     0.09      0.03     0.03     0.16 1.00     3858     3521
sDev_Yr_1                  2.01      0.09     1.86     2.22 1.00     3677     3162

抽样采用sampling(NUTS)方法。对于每个参数,Bulk_ESS和Tail_ESS为有效样本量指标,Rhat为拆分链的潜在尺度缩减因子(收敛时Rhat=1)。
警告信息:
热身完成后出现5次发散转移。将adapt_delta提高到0.99以上可能有所帮助。
当前先验设置摘要
priorclasscoefgrouprespdparnlparlbubsource
(flat)bdefault
normal(0.02, 0.01)bCal_Yr_Timeuser
normal(1, 0.95)bDev_Yr_1_Factor2user
(flat)bsDev_Yr_1(vectorized)
(flat)bsigmadefault
student_t(3, 0.1, 0.05)bDev_Yr_10_Splinesigmauser
normal(-0.1, 0.05)bDev_Yr_6_Capsigmauser
normal(0.2, 0.1)bInterceptsigmauser
student_t(3, 4.4, 2.5)Interceptdefault
student_t(3, 0, 2.5)sds0default
student_t(3, 0, 2.5)sdss(Dev_Yr, k = 3, m = 2)0(vectorized)
解决方案

在brms中,GAM的平滑项s(Dev_Yr)会被拆分为两类参数,需要分别设置先验:

1. 平滑基函数的系数(对应sDev_Yr_1)

sDev_Yr_1是平滑项s(Dev_Yr, k=3, m=2)的基函数系数(因k=3,实际包含多个系数,摘要中显示的是整体汇总值)。设置先验时需结合Dev_Yr的取值范围调整先验尺度:

  • 如果Dev_Yr取值范围大,可适当放大先验标准差,避免过度约束;反之则缩小。
  • 示例:给sDev_Yr_1设置正态先验:
set_prior("normal(0, 5)", class = "b", coef = "sDev_Yr_1")

2. 平滑项的标准差(对应sds(sDev_Yr_1))

这个参数控制整个平滑曲线的波动幅度,设置合适的先验可避免曲线过度拟合或欠拟合:

  • 示例:给平滑项标准差设置半学生t先验:
set_prior("student_t(3, 0, 3)", class = "sds", coef = "s(Dev_Yr, k = 3, m = 2)")

完整先验设置示例

将上述先验与已有先验整合:

GAM_prior <- c(
  # 平滑系数sDev_Yr_1的非平坦先验
  set_prior("normal(0, 5)", class = "b", coef = "sDev_Yr_1"),
  # 平滑项标准差的先验
  set_prior("student_t(3, 0, 3)", class = "sds", coef = "s(Dev_Yr, k = 3, m = 2)"),
  # 原有其他先验
  set_prior("normal(0.02, 0.01)", class = "b", coef = "Cal_Yr_Time"),
  set_prior("normal(1, 0.95)", class = "b", coef = "Dev_Yr_1_Factor2"),
  set_prior("student_t(3, 0.1, 0.05)", class = "b", coef = "Dev_Yr_10_Spline", dpar = "sigma"),
  set_prior("normal(-0.1, 0.05)", class = "b", coef = "Dev_Yr_6_Cap", dpar = "sigma"),
  set_prior("normal(0.2, 0.1)", class = "b", coef = "Intercept", dpar = "sigma")
)

验证先验设置

运行prior_summary(Model_GAM)可以检查先验是否正确应用,确保sDev_Yr_1的先验已从默认平坦改为自定义的非平坦先验。

发散转移问题处理

针对模型出现的发散转移警告,可尝试将adapt_delta提高至0.995:

control = list(adapt_delta = .995 )

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.30 19:18:32