【问题标题】:sklearn DecisionTreeClassifier with CountVectorizer and additional predictor带有 CountVectorizer 和附加预测器的 sklearn DecisionTreeClassifier
【发布时间】:2020-09-08 15:24:25
【问题描述】:

我已经用 sklearn 的DecisionTreeClassifier 建立了一个文本分类模型,并想添加另一个预测器。我的数据位于 pandas 数据框中,其列标记为 'Impression'(文本)、'Volume'(浮点数)和 'Cancer'(标签)。我一直只使用印象来预测癌症,但想使用印象和体积来预测癌症。

我之前运行没有问题的代码:

X_train, X_test, y_train, y_test = train_test_split(data['Impression'], data['Cancer'], test_size=0.2)

vectorizer = CountVectorizer()
X_train = vectorizer.fit_transform(X_train)
X_test = vectorizer.transform(X_test)

dt = DecisionTreeClassifier(class_weight='balanced', max_depth=6, min_samples_leaf=3, max_leaf_nodes=20)
dt.fit(X_train, y_train)
y_pred = dt.predict(X_test)

我尝试了几种不同的方法来添加音量预测器(更改为粗体):

1) 仅fit_transform 印象数

X_train, X_test, y_train, y_test = train_test_split(data[['Impression', 'Volume']], data['Cancer'], test_size=0.2)

vectorizer = CountVectorizer()
X_train['Impression'] = vectorizer.fit_transform(X_train['Impression'])
X_test = vectorizer.transform(X_test)

dt = DecisionTreeClassifier(class_weight='balanced', max_depth=6, min_samples_leaf=3, max_leaf_nodes=20)
dt.fit(X_train, y_train)
y_pred = dt.predict(X_test)

这会引发错误

TypeError: float() argument must be a string or a number, not 'csr_matrix'
...
ValueError: setting an array element with a sequence.

2) 致电fit_transform 了解展示次数和数量。除了fit_transform 行之外的代码与上面相同:

X_train = vectorizer.fit_transform(X_train)

这当然会抛出错误:

ValueError: Number of labels=1800 does not match number of samples=2
...
X_train.shape
(2, 2)
y_train.shape
(1800,)

我很确定方法 #1 是正确的方法,但我无法找到任何教程或解决方案来说明如何将浮点预测器添加到此文本分类模型中。

任何帮助将不胜感激!

【问题讨论】:

    标签: python machine-learning scikit-learn decision-tree


    【解决方案1】:

    ColumnTransformer() 正好解决了这个问题。我们可以将remainder 参数设置为ColumnTransformer 中的passthrough,而不是手动将CountVectorizer 的输出附加到其他列。

    from sklearn.tree import DecisionTreeClassifier
    from sklearn.model_selection import train_test_split
    from sklearn.pipeline import make_pipeline
    from sklearn.compose import make_column_transformer
    from sklearn.feature_extraction.text import CountVectorizer
    import pandas as pd
    from sklearn import set_config
    
    set_config(print_changed_only='True', display='diagram')
    
    data = pd.DataFrame({'Impression': ['this is the first text',
                                        'second one goes like this',
                                        'third one is very short',
                                        'This is the final statement'],
                         'Volume': [123, 1, 2, 123],
                         'Cancer': [1, 0, 0, 1]})
    
    X_train, X_test, y_train, y_test = train_test_split(
        data[['Impression', 'Volume']], data['Cancer'], test_size=0.5)
    
    ct = make_column_transformer(
        (CountVectorizer(), 'Impression'), remainder='passthrough')
    
    pipeline = make_pipeline(ct, DecisionTreeClassifier())
    pipeline.fit(X_train, y_train)
    pipeline.score(X_test, y_test)
    

    使用 0.23.0 版本,查看管道对象的视觉效果(set_config 中的display 参数)

    【讨论】:

      【解决方案2】:

      您可以使用hstack 将两个功能组合在一起。

      from scipy.sparse import hstack
      X_train = vectorizer.fit_transform(X_train)
      X_train_new = hstack(X_train, np.array(data['Volume']))
      

      现在您的新火车包含这两个功能。如果我可以建议,请使用 tfidfvectorizer 而不是 countvectorizer,因为 tfidf 考虑每个文档/印象中单词的重要性,而 countvectorizer 只计算单词的出现次数,因此像“THE”这样的单词将比那些真正重要的单词具有更高的重要性我们。

      【讨论】:

        猜你喜欢
        • 2020-09-12
        • 2018-03-20
        • 2020-02-05
        • 2020-01-31
        • 2018-05-05
        • 2019-11-08
        • 2017-09-09
        • 2016-02-07
        • 2018-05-05
        相关资源
        最近更新 更多