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

scikit-learn中如何为稀疏分类特征加权调整评分?

解决方案

一、核心思路纠正:区分特征加权与样本加权

你要的是特征加权而非样本加权,之前用sample_weight的思路方向错了,这也是交叉验证时权重长度不匹配报错的根源。sample_weight是给每个样本整体加权,而你的需求是降低稀疏分类特征对模型的影响,这属于特征层面的权重调整。

二、针对稀疏分类特征的特征加权方案

1. 特征工程阶段:对稀疏分类特征进行缩放

先统计每个分类特征下各类别的出现频次,对该特征的编码值乘以基于频次的权重系数,稀疏类别(频次低)的系数小于1,从而降低特征数值幅度,削弱其对模型的影响。

示例代码:

import pandas as pd

# 假设df是数据集,cat_col是某稀疏分类特征列
freq = df['cat_col'].value_counts(normalize=True)
# 定义权重映射:频次越低,权重越小
weight_map = freq.apply(lambda x: x**0.5).to_dict()
# 对特征列进行加权缩放
df['cat_col_weighted'] = df['cat_col'].map(weight_map)

后续用加权后的特征列替代原分类特征列参与训练即可。

2. 高斯过程核函数自定义:给特征分配不同长度尺度

高斯过程核函数(如RBF、Matern)的length_scale参数控制特征对输出的影响:length_scale越大,特征变化对预测值的影响越小。给稀疏分类特征设置更大的length_scale,就能降低它们的权重。

示例代码(结合GridSearchCV优化):

from sklearn.gaussian_process import GaussianProcessRegressor
from sklearn.gaussian_process.kernels import RBF, WhiteKernel
from sklearn.model_selection import GridSearchCV

# 假设共有10个特征,前3个是稀疏分类特征(已编码为数值),后7个是数值特征
n_features = 10
# 初始化核函数,length_scale数组对应每个特征的长度尺度
kernel = RBF(length_scale=[1.0]*n_features) + WhiteKernel()

# 参数网格:给前3个稀疏特征设置更大的length_scale候选值
param_grid = {
    'kernel__k1__length_scale': [
        [5.0,5.0,5.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0],
        [10.0,10.0,10.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0]
    ]
}

gpr = GaussianProcessRegressor(kernel=kernel)
grid_search = GridSearchCV(gpr, param_grid, scoring='r2', cv=5)
grid_search.fit(X, y)

通过GridSearchCV可自动找到最优的特征长度尺度组合,实现对稀疏特征的加权抑制。

三、若坚持使用样本加权(非最优方案)

如果需要针对包含稀疏特征的样本降低权重,可通过闭包捕获权重数组,利用样本索引提取对应权重,解决交叉验证时的长度不匹配问题:

from sklearn.metrics import r2_score
from sklearn.metrics import make_scorer

# 预计算全量样本权重:包含稀疏类别的样本权重更低
sample_weights = ...  # 你的全量样本权重数组,长度为329

def create_weighted_r2_scorer(weights):
    def weighted_r2(y_true, y_pred, X_test):
        # 提取测试集样本对应的权重
        test_indices = X_test.index
        test_weights = weights.loc[test_indices]
        return r2_score(y_true, y_pred, sample_weight=test_weights)
    # 设置needs_X=True,让scorer传入X_test以获取索引
    return make_scorer(weighted_r2, greater_is_better=True, needs_X=True)

# 创建scorer并传入GridSearchCV
weighted_r2_scorer = create_weighted_r2_scorer(sample_weights)
grid_search = GridSearchCV(gpr, param_grid, scoring=weighted_r2_scorer, cv=5)

内容的提问来源于stack exchange,提问作者David Siret Marquès

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.23 13:07:46