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

在R tidymodels中如何为指定变量设置sum to zero对比

问题解答

需求可行性结论

你的需求完全可以实现,无需修改全局对比配置,也不会影响其他变量的默认对比规则。你现有代码的核心问题是step_dummy中加了one_hot = TRUE,该参数会生成n个全量虚拟变量,和base R中contr.sum生成n-1个虚拟变量的求和约束逻辑冲突,因此拟合结果和基准代码不一致。

推荐实现方案

方案1:在recipe的step_dummy中指定专属对比

直接利用step_dummy的contrasts参数为指定变量单独设置对比规则,其余变量默认使用全局对照配置:

library(tidymodels)
Bikeshare <- ISLR2::Bikeshare  

# 模型声明
lm_spec <- linear_reg() %>%
  set_engine("lm")

# 配方配置,仅为mnth和hr设置sum to zero对比
the_rec <- 
  recipe(
    bikers ~ mnth + hr + workingday + temp + weathersit,
    data = Bikeshare
  ) %>%
  step_dummy(c(mnth, hr), 
             contrasts = list(mnth = contr.sum(12), hr = contr.sum(24)))

# 工作流装配与拟合
the_workflow <- workflow() %>% 
  add_recipe(the_rec) %>% 
  add_model(lm_spec)

the_workflow_fit <- fit(the_workflow, data = Bikeshare)
mod_tidy <- extract_fit_parsnip(the_workflow_fit)

# 验证和base R结果一致,会返回TRUE
all.equal(coef(mod_tidy$fit), coef(mod.lm2))

方案2:在模型引擎参数中指定对比

不需要在recipe中处理虚拟变量,直接将自定义对比规则传给lm引擎的contrasts参数,实现效果完全一致:

library(tidymodels)
Bikeshare <- ISLR2::Bikeshare  

# 模型声明时直接指定专属对比
lm_spec <- linear_reg() %>%
  set_engine("lm", contrasts = list(mnth = contr.sum(12), hr = contr.sum(24)))

# 配方不需要额外处理分类变量
the_rec <- recipe(
  bikers ~ mnth + hr + workingday + temp + weathersit,
  data = Bikeshare
)

# 工作流装配与拟合
the_workflow <- workflow() %>% 
  add_recipe(the_rec) %>% 
  add_model(lm_spec)

the_workflow_fit <- fit(the_workflow, data = Bikeshare)

两种方案都不会修改全局options中的对比规则,其他分类变量(如workingday、weathersit)仍会使用默认的treatment对比,完全符合你的需求。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.26 01:15:06