scikit-learn 在管道中使用多个类预处理 SVM

Posted

技术标签:

【中文标题】scikit-learn 在管道中使用多个类预处理 SVM【英文标题】:scikit-learn preprocessing SVM with multiple classes in a pipeline 【发布时间】:2013-04-14 19:21:09 【问题描述】:

有关机器学习的文献强烈建议对 SVM 的数据进行标准化 (Preprocessing data in scikit-learn)。和answered before 一样,同样的StandardScalar 应该应用于训练和测试数据。

    使用StandardScalar 与手动减去平均值并除以标准差相比有什么优势(除了在管道中使用它的能力)? scikit-learn 中的 LinearSVC 依赖于 one-vs-the-rest 用于多个类(正如 larsmans 所提到的,SVC 依赖于多类的一对一)。那么,如果我有多个类使用规范化作为第一个估计量的管道进行训练,会发生什么?它还会计算每个类别的均值和标准变差,并在分类时使用吗? 更具体地说,以下分类器是否在流水线的 svm 阶段之前对每个类应用不同的均值和标准差?
estimators = [('normalize', StandardScaler()), ('svm', SVC(class_weight = 'auto'))]
clf = Pipeline(estimators)
# Training
clf.fit(X_train, y)
# Classification
clf.predict(X_test)

【问题讨论】:

SVC 是否为多类案例进行 OvR 训练;那是您所指的LinearSVCSVC 的行为由 multiclass 参数控制,默认为 OvO(一对一)。 @larsmans- 感谢您的更正,我将更新文本以避免它被索引。 【参考方案1】:

StandardScaler 执行的特征缩放是在不参考目标类的情况下执行的。它只考虑X 特征矩阵。它计算所有样本中每个特征的均值和标准差,与每个样本的目标类别无关。

管道的每个组件独立运行:只有数据在它们之间传递。让我们扩展管道的clf.fit(X_train, y)。它大致做了以下事情:

X_train_scaled = clf.named_steps['normalize'].fit_transform(X_train, y)
clf.named_steps['svm'].fit(X_train_scaled, y)

第一个缩放步骤实际上忽略了它传递的y,而是计算X_train中每个特征的均值和标准差,并将它们存储在其mean_std_属性中(fit组件)。它还将X_train 居中并返回它(transform 组件)。下一步学习 SVM 模型,并执行 one-vs-rest 所需的操作。

现在是管道的分类视角。 clf.predict(X_test) 扩展为:

X_test_scaled = clf.named_steps['normalize'].transform(X_test)
y_pred = clf.named_steps['svm'].predict(X_test_scaled)

返回y_pred。在第一行中,它使用存储的mean_std_ 使用从训练数据中学习的参数将转换应用于X_test

是的,缩放算法不是很复杂。它只是减去平均值并除以标准。但是StandardScalar

为算法提供一个名称,以便您将其从库中提取出来 避免你自己动手,确保它正常工作,并且不需要你了解它在内部做什么 记住来自fitfit_transform 的参数以供以后的transform 操作(如上) 提供与其他数据转换相同的接口(因此可以在管道中使用) 在密集或稀疏矩阵上运行 能够使用其inverse_transform 方法反转转换

【讨论】:

以上是关于scikit-learn 在管道中使用多个类预处理 SVM的主要内容,如果未能解决你的问题,请参考以下文章

在管道中使用时带有 scikit-learn PLSRegression 的 ValueError

scikit-learn:如何使用管道组合 LabelEncoder 和 OneHotEncoder?

scikit-learn:应用任意函数作为管道的一部分

当最后一个估计器不是转换器时,如何使用 scikit-learn 管道进行转换?

scikit-learn:在管道中使用 SelectKBest 时获取选定的功能

在 SciKit-Learn 中使用管道的排列重要性