【问题标题】:How to apply standardization to SVMs in scikit-learn?如何在 scikit-learn 中对 SVM 应用标准化?
【发布时间】:2013-01-19 06:00:02
【问题描述】:

我正在使用 scikit-learn 的当前稳定版本 0.13。我正在使用 sklearn.svm.LinearSVC 类对一些数据应用线性支持向量分类器。

在 scikit-learn 文档中的 chapter about preprocessing 中,我阅读了以下内容:

学习算法的目标函数中使用的许多元素(例如支持向量机的 RBF 内核或线性模型的 l1 和 l2 正则化器)假设所有特征都以零为中心并且具有相同顺序的方差。如果一个特征的方差比其他特征大几个数量级,它可能会主导目标函数并使估计器无法按预期正确地从其他特征中学习。

问题 1:标准化对一般的 SVM 有用吗?也适用于像我这样具有线性核函数的那些?

问题 2: 据我了解,我必须计算训练数据的均值和标准差,并使用 sklearn.preprocessing.StandardScaler 类对测试数据应用相同的转换。但是,我不明白的是,在将训练数据输入 SVM 分类器之前,我是否必须同时转换训练数据或仅转换测试数据。

也就是说,我必须这样做吗:

scaler = StandardScaler()
scaler.fit(X_train)                # only compute mean and std here
X_test = scaler.transform(X_test)  # perform standardization by centering and scaling

clf = LinearSVC()
clf.fit(X_train, y_train)
clf.predict(X_test)

或者我必须这样做:

scaler = StandardScaler()
X_train = scaler.fit_transform(X_train)  # compute mean, std and transform training data as well
X_test = scaler.transform(X_test)  # same as above

clf = LinearSVC()
clf.fit(X_train, y_train)
clf.predict(X_test)

简而言之,我是否必须在训练数据上使用scaler.fit(X_train)scaler.fit_transform(X_train) 才能通过LinearSVC 获得合理的结果?

【问题讨论】:

    标签: python scikit-learn classification svm normalization


    【解决方案1】:

    都没有。

    scaler.transform(X_train) 没有任何作用。 transform 操作未到位。 你必须这样做

    X_train = scaler.fit_transform(X_train)
    
    X_test = scaler.transform(X_test)
    

    X_train = scaler.fit(X_train).transform(X_train)
    

    您始终需要对训练或测试数据进行相同的预处理。是的,标准化总是好的,如果它反映了你对数据的信念。 特别是对于 kernel-svm,它通常是至关重要的。

    【讨论】:

    • 当然,我知道这一点。我只是懒得发布它(我感到羞耻)。关键是在X_train上使用fit()还是fit_transform()
    • 添加了评论。再次改写您的问题,这与fitfit_transform 无关,而是是否要同时转换测试和训练数据。答案是:肯定的。如果你只改造一个,你怎么能期望学到任何东西?他们将不再来自同一个分布。
    • 好吧,这就是我想知道的。我对 SVM 很陌生,有点困惑。无论如何,感谢您的快速反应。 :)
    • @AndreasMueller 如果我使用梯度提升分类,是否需要扩展我的特征?
    • 如果您将树用作弱学习器,则不会。所有基于树的模型都与缩放无关。
    【解决方案2】:

    为什么不使用Pipeline 一次性链接(或组合)转换器和估算器?为您省去分别拟合和转换数据然后使用估算器的麻烦。也可以节省一些空间。

    from sklearn.pipeline import Pipeline
    
    pipe_lrSVC = Pipeline([('scaler', StandardScaler()), ('clf', LinearSVC())])
    pipe_lrSVC.fit(X_train, y_train)
    y_pred = pipe_lrSVC.predict(X_test)
    

    【讨论】:

      猜你喜欢
      • 2021-01-15
      • 2014-03-31
      • 2016-04-18
      • 2014-10-17
      • 2016-05-08
      • 2018-08-12
      • 2019-11-14
      • 2019-01-14
      • 2018-12-19
      相关资源
      最近更新 更多