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

在R中拟合分段线性混合效应回归模型如何避免奇异性错误?

线性混合效应模型拟合纵向临床试验数据的共线性问题解决思路

问题场景与原模型问题

我用线性混合效应模型拟合两臂临床试验的纵向血红蛋白(Hb)计数长格式数据,数据子集如下:

pid  site  arm pday Hb  pday2 I
1 MOB2004_001 Boane  SP    0  8.5     0 0
2 MOB2004_001 Boane  SP    3  8.0     9 0
3 MOB2004_001 Boane  SP    7  8.9    49 1
4 MOB2004_001 Boane  SP   14  8.9   196 1
5 MOB2004_002 Boane  SP    0 11.5     0 0
6 MOB2004_002 Boane  SP    3  9.1     9 0

观察均值响应曲线后,我希望建模Hb与时间的二次关系,且在第3天前后使用不同参数,因此创建指示变量I(pday<3时为0,否则为1)。同时需要评估研究组间差异,必须包含研究组-时间交互项。

原模型设定如下:

lme(data=dat.mod2, fixed=Hb~ arm*pday + pday*I + pday2 + 
    pday2*I , random=~1|site/pid, na.action = na.omit)

对应的模型公式:
$$ Hb_{ik} = \beta_{00} + \beta_{01}*I + \beta_{10}*day + \beta_{11}*dayI + \beta_{20}day^2 + \beta_{21}day^2I + \beta_3arm_i + \beta_4 *arm_iday + u_{ik} + v_{k} $$

拟合时出现共线性错误:

Error in MEEM(object, conLin, control$niterEM) :
Singularity in backsolve at level 0, block 1

单独包含pday*I或pday2*I时模型可正常拟合,但同时包含就触发错误;用lme4的lmer拟合也出现秩亏缺问题。我需要估计节点前后的二次项,不希望使用平滑处理。

问题根源

核心错误是指示变量I与原时间项的交互引发多重共线性:

  • 当I=0时,pday*I和pday2*I均为0,时间项仅由pday和pday2构成;
  • 当I=1时,时间项变为pday + pday*I + pday2 + pday2*I = pday*(1+I) + pday2*(1+I),本质是原时间项的线性缩放,导致变量间存在完全线性依赖,模型矩阵秩亏缺。

正确建模思路

要实现节点前后的分段二次模型,需重构时间变量,避免共线性:

方法1:构建分段时间变量(推荐)

创建以第3天为节点的分段时间变量,将节点前后的时间拆分为独立变量:

  1. 生成新变量:
    • t1:pday<3时取pday值,否则为0(节点前的时间)
    • t2:pday>=3时取pday-3(节点后从0开始计数的时间),否则为0
    • 同时生成平方项t1_sq = t1^2、t2_sq = t2^2
  2. 模型设定:包含分组、分段时间的线性/二次项,以及分组与各时间项的交互,确保组间差异可评估。

R代码示例:

# 生成分段时间变量
dat.mod2 <- dat.mod2 %>%
  mutate(
    t1 = ifelse(pday < 3, pday, 0),
    t2 = ifelse(pday >= 3, pday - 3, 0),
    t1_sq = t1^2,
    t2_sq = t2^2
  )

# 拟合lme模型
fit_lme <- lme(
  data = dat.mod2,
  fixed = Hb ~ arm + t1 + t1_sq + t2 + t2_sq + 
           arm:t1 + arm:t1_sq + arm:t2 + arm:t2_sq,
  random = ~1|site/pid,
  na.action = na.omit
)

该设定下,t1和t2不会同时非零,彻底消除共线性,且能分别估计节点前后的二次趋势及组间差异。

方法2:中心化时间变量后结合指示变量

若坚持使用原指示变量I,需先将时间变量中心化到节点(第3天),减少共线性风险:

  1. 生成中心化时间变量cent_pday = pday - 3及平方项cent_pday_sq = cent_pday^2
  2. 模型中纳入分组与中心化时间的交互、指示变量与中心化时间的交互

R代码示例:

# 生成中心化时间变量
dat.mod2 <- dat.mod2 %>%
  mutate(
    cent_pday = pday - 3,
    cent_pday_sq = cent_pday^2
  )

# 拟合模型
fit_lme <- lme(
  data = dat.mod2,
  fixed = Hb ~ arm*cent_pday + arm*cent_pday_sq + I*cent_pday + I*cent_pday_sq,
  random = ~1|site/pid,
  na.action = na.omit
)

需注意:拟合前建议用cor()检查变量相关性,或用car::vif()计算方差膨胀因子(VIF<5为可接受范围),确保无强共线性。

验证步骤

  • 拟合前检查固定效应变量间的相关性,相关系数>0.7提示强共线性;
  • 用方差膨胀因子(VIF)量化共线性程度,VIF>10需调整模型;
  • 逐步添加变量,定位触发秩亏缺的变量组合,验证模型设定合理性。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.20 21:32:54