求助:mgcv中带定点约束的惩罚三次样条GAM模型预测问题
解决mgcv约束过定点GAM模型的预测问题
问题根源
- 模型中的
X是矩阵类型(样条基矩阵),预测时传入numeric类型的X会触发类型不匹配错误 - 用list构建模型时错误地将惩罚矩阵
S放入data列表,导致维度不匹配(S是8×8矩阵,其他变量为100行向量)
正确的模型拟合(list作为data参数)
修正模型拟合逻辑,惩罚矩阵S无需放入data列表,仅通过paraPen参数指定:
library(mgcv) set.seed(0) n <- 100 x <- runif(n)*4-1;x <- sort(x); f <- exp(4*x)/(1+exp(4*x));y <- f+rnorm(100)*0.1;plot(x,y) dat <- data.frame(x=x,y=y) # 构造带约束点节点的样条基与惩罚矩阵 knots <- data.frame(x=seq(-1,3,length=9)) sm <- smoothCon(s(x,k=9,bs="cr"),dat,knots=knots)[[1]] # 移除约束点对应的基列,构造偏移项 X <- sm$X[,-3] # 8列样条基矩阵 S <- sm$S[[1]][-3,-3] # 对应维度的惩罚矩阵 off <- y*0 + .6 # 偏移项,强制曲线过(0, 0.6) # 构造data列表:仅包含模型用到的变量,S不放入其中 list.dat <- list(y = y, X = X, off = off) # 拟合约束GAM模型 b <- gam(y ~ X - 1 + offset(off), data = list.dat, paraPen=list(X=list(S))) lines(x,predict(b)) # 验证拟合曲线
正确的预测步骤
核心是为新x值生成与模型结构完全一致的样条基矩阵,确保变量类型匹配:
# 生成待预测的x序列 x_seq <- seq(-1, 3, length.out = 10000) new_raw_dat <- data.frame(x = x_seq) # 为新x值生成样条基矩阵,注意使用原始自变量名x sm_new <- smoothCon(s(x,k=9,bs="cr"), new_raw_dat, knots=knots)[[1]] X_new <- sm_new$X[,-3] # 移除第3列,和模型中的X结构对齐 # 构造预测用的list数据:X为矩阵,off长度与新数据一致 predict_list <- list( X = X_new, off = rep(0.6, length(x_seq)) # 偏移项保持与原模型一致 ) # 执行预测 predictions <- predict(b, newdata = predict_list, se.fit = TRUE) # 可视化预测结果 lines(x_seq, predictions$fit, col="red", lwd=2)
关键注意事项
- 模型中的
X是矩阵,预测时必须传入同维度的矩阵,不能传入numeric向量 - 惩罚矩阵
S是模型拟合参数,无需放入data列表,仅通过paraPen指定 - 生成新样条基时,要使用原始自变量名(
x)而非模型中的X,smoothCon需基于原始变量生成基 - 偏移项
off的长度必须与新数据行数完全匹配
内容的提问来源于stack exchange,提问作者Gretel
相关产品推荐
相关产品推荐

