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

mlr3高基数因子编码col_roles报错求助(更新包后仍存在)

mlr3空间任务中使用Impact编码训练glmnet模型的列角色错误解决

问题描述

尝试用mlr3包训练glmnet模型,针对27水平的高基数分类变量采用Impact编码,运行时出现如下错误:

Error in .__Task__col_roles(self = self, private = private, super = super,  : 
  Assertion on 'names of col_roles' failed: Names must be a permutation of set {'feature','target','name','order','stratum','group','weight','coordinate','space','time'}, but has extra elements {'always_included'}.
This happened PipeOp high_cardinality_encoding's $train()

核心代码如下:

data <- read.csv("C:/Users/test.csv")
data$presence <- as.factor(data$presence)
data$habitat <- as.factor(data$habitat)
classif_task_sp <- mlr3spatial::as_task_classif_st(id = "A1", x = data[, which(!(names(data) %in% c("ID", "year")))], target = "presence", positive = "1", 
                                                   coordinate_names = c("x", "y"), crs = "EPSG:4326", coords_as_features = FALSE)
classif_task_sp$set_col_roles("presence", roles = c("target", "stratum"))
partition_classif_task_sp <- mlr3::partition(classif_task_sp, ratio = 0.67)

factor_encoding <- mlr3pipelines::po("removeconstants") %>%
  mlr3pipelines::po("encodeimpact", affect_columns = selector_cardinality_greater_than(10), id = "high_cardinality_encoding") %>%
  mlr3pipelines::po("encode", method = "one-hot", affect_columns = selector_cardinality_greater_than(3), id = "low_cardinality_encoding") %>%
  mlr3pipelines::po("encode", method = "treatment", affect_columns = selector_type("factor"), id = "binary_encoding")

learner_glmnet <- mlr3tuningspaces::lts(mlr3::lrn("classif.glmnet", predict_type = "prob", standardize = FALSE))
learner_glmnet_factor_encoding <- mlr3::as_learner(factor_encoding %>% learner_glmnet)

tuning <- mlr3tuning::auto_tuner(tuner = mlr3tuning::tnr("grid_search", resolution = 5, batch_size = 10),
                                 learner = learner_glmnet_factor_encoding,
                                 resampling = mlr3::rsmp("spcv_coords", folds = 2),
                                 measure = mlr3::msr("classif.prauc"),
                                 terminator = mlr3tuning::trm("evals", n_evals = 2, k = 0))

run_resampling <- mlr3::resample(classif_task_sp, learner = tuning, resampling = mlr3::rsmp("spcv_coords", folds = 2), store_models = TRUE)

run_training <- tuning$train(classif_task_sp, row_ids = partition_classif_task_sp$train)

已更新mlr3至0.21.1、mlr3fselect至1.2.1,错误仍存在。

问题分析

错误根源是mlr3spatial的空间分类任务(TaskClassifST)仅支持固定的标准列角色列表,而流程中引入了mlr3fselect模块的always_included非标准角色,导致角色校验失败。该角色可能来自编码管道的重复变量处理、调优组件的隐式配置冲突。

解决方案

1. 修复编码管道的选择器,避免重复处理

当前编码管道的选择器存在重叠(比如高基数变量可能被后续one-hot/treatment编码再次处理),调整选择器明确划分处理范围:

factor_encoding <- mlr3pipelines::po("removeconstants") %>%
  # 处理基数>10的高基数变量
  mlr3pipelines::po("encodeimpact", 
                    affect_columns = selector_cardinality_greater_than(10), 
                    id = "high_cardinality_encoding") %>%
  # 处理基数4-10的中基数变量
  mlr3pipelines::po("encode", method = "one-hot", 
                    affect_columns = selector_cardinality_between(4, 10), 
                    id = "low_cardinality_encoding") %>%
  # 处理基数≤3的低基数变量
  mlr3pipelines::po("encode", method = "treatment", 
                    affect_columns = selector_cardinality_less_than_or_equal_to(3), 
                    id = "binary_encoding")

2. 移除非标准列角色

在任务传入管道前,手动清理不被支持的列角色:

# 定义空间任务允许的标准列角色
allowed_roles <- c("feature","target","name","order","stratum","group","weight","coordinate","space","time")
# 过滤掉非标准角色
classif_task_sp$col_roles <- classif_task_sp$col_roles[names(classif_task_sp$col_roles) %in% allowed_roles]

3. 调整调优学习器的创建方式

mlr3tuningspaces::lts()可能隐式添加特征选择相关配置,改用基础学习器手动绑定调优空间:

# 创建基础glmnet学习器
learner_glmnet <- mlr3::lrn("classif.glmnet", predict_type = "prob", standardize = FALSE)
# 绑定glmnet的默认调优空间
learner_glmnet$param_set <- mlr3tuningspaces::ts("classif.glmnet.default")$param_set

4. 逐步排查验证

先跳过调优流程,测试编码管道+学习器的基础训练,确认编码逻辑无问题:

# 测试基础训练流程
test_learner <- mlr3::as_learner(factor_encoding %>% learner_glmnet)
test_train <- test_learner$train(classif_task_sp, row_ids = partition_classif_task_sp$train)

若基础训练正常,再逐步添加调优组件排查冲突点。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.16 05:59:53