XGBoost分类变量:Dummification与编码

时间:2015-12-14 10:48:23

标签: python categorical-data xgboost

使用XGBoost时,我们需要将分类变量转换为数字。

以下方法之间的绩效/评估指标是否存在差异:

  1. 对您的分类变量进行虚假化
  2. 对您的分类变量进行编码,例如: (a,b,c)至(1,2,3)
  3. ALSO:

    是否有任何理由不使用方法2,例如使用labelencoder

4 个答案:

答案 0 :(得分:39)

public partial class MainWindow : Window { Image img = new Image(); public MainWindow() { InitializeComponent(); } private void Button_Click(object sender, RoutedEventArgs e) { Canvas.SetLeft(img, 200.0); Canvas.SetTop(img, 200.0); 仅处理数字列。

如果你有一个功能xgboost来描述一个分类变量(,即没有数字关系

使用LabelEncoder您只需拥有:

[a,b,b,c]

array([0, 1, 1, 2]) 会错误地将此功能解释为具有数字关系!这只会将每个字符串Xgboost映射为整数,仅此而已。

正确的方式

使用OneHotEncoder,您最终会得到:

('a','b','c')

这是array([[ 1., 0., 0.], [ 0., 1., 0.], [ 0., 1., 0.], [ 0., 0., 1.]]) 或任何其他机器学习工具的分类变量的正确表示

Pandas get_dummies是一个很好的创建虚拟变量的工具(在我看来,更容易使用)。

上述问题中的方法#2不能正确表示数据

答案 1 :(得分:4)

我想回答这个问题,不仅仅是在XGBoost方面,而是在处理分类数据的任何问题方面。虽然“dummification”会创建一个非常稀疏的设置,特别是如果您有多个具有不同级别的分类列,标签编码通常会有偏差,因为数学表示不能反映级别之间的关系。

对于二进制分类问题,在传统信用评分模型中高度利用的天才但未开发的方法是使用证据权重来替换分类级别。基本上每个分类级别都被商品比例/坏比例所取代。

可以详细了解here

Python库here

此方法允许您捕获一列下的“级别”,并避免通过虚假或编码产生的稀疏性或诱导偏差。

希望这有帮助!

答案 2 :(得分:0)

2020 年 11 月 23 日

XGBoost 从 1.3.0 版开始添加了对分类特征的实验性支持。来自文档:

<块引用>

1.8.7 分类数据

除了用户执行编码,XGBoost 有实验支持 对于使用 gpu_histgpu_predictor 的分类数据。没有特别的 需要对输入的测试数据进行操作,因为信息 在训练期间,关于类别的信息被编码到模型中。

https://buildmedia.readthedocs.org/media/pdf/xgboost/latest/xgboost.pdf

在 DMatrix 部分,文档还说:

<块引用>

enable_categorical (boolean, optional) – 1.3.0 新版本。

对分类特征专业化的实验支持。不要 除非您对开发感兴趣,否则设置为 True。目前是 仅可用于 gpu_hist 树方法与 1 vs 休息(一个热) 分类拆分。此外,JSON 序列化格式、gpu_predictor 和 需要熊猫输入。

答案 3 :(得分:-2)

这里是一个代码示例,该示例将“热编码”列添加到具有“分类”列的Pandas DataFrame中:

ONE_HOT_COLS = ["categorical_col1", "categorical_col2", "categorical_col3"]
print("Starting DF shape: %d, %d" % df.shape)


for col in ONE_HOT_COLS:
    s = df[col].unique()

    # Create a One Hot Dataframe with 1 row for each unique value
    one_hot_df = pd.get_dummies(s, prefix='%s_' % col)
    one_hot_df[col] = s

    print("Adding One Hot values for %s (the column has %d unique values)" % (col, len(s)))
    pre_len = len(df)

    # Merge the one hot columns
    df = df.merge(one_hot_df, on=[col], how="left")
    assert len(df) == pre_len
    print(df.shape)