美文网首页机器学习
通过一个小案例熟悉决策树算法中的参数

通过一个小案例熟悉决策树算法中的参数

作者: 木头里有虫911 | 来源:发表于2020-08-23 22:28 被阅读0次

    在上一期内容中,我们介绍了决策树算法的基本流程。这里总结一下决策树算法的主要优点:

    1. 具有很好的解释性,模型可以生成可以理解的规则。这一点在某些需要提取分类规则的场景中被广泛的应用,而其他机器学习模型在这一点很难做到。例如在医疗辅助系统中,为了方便专业人员发现错误,常常将决策树算法用于辅助病症检测。
    2. 可以发现特征的重要程度。
    3. 模型的计算复杂度较低

    同时,决策树算法也存在如下缺点:

    1. 模型容易过拟合,需要采用减枝技术处理。
    2. 不能很好利用连续型特征。这一点我们在鸢尾花数据集分类中也深有体会。当某个特征的值在某一区间内的分布较为均衡时,即决策边界比较模糊时,算法的误差会比较大
    3. 预测能力有限,无法达到其他强监督模型效果。
    4. 方差较高,数据分布的轻微改变很容易造成树结构完全不同。

    由于决策树模型中自变量与因变量的非线性关系以及决策树简单的计算方法,使得它成为集成学习中最为广泛使用的基模型。梯度提升树(GBDT),XGBoost以及LightGBM等先进的集成模型都采用了决策树作为基模型,在广告计算、CTR预估、金融风控等领域大放异彩,成为当今与神经网络相提并论的复杂模型,更是数据挖掘比赛中的常客。在新的研究中,南京大学周志华老师提出一种多粒度级联森林模型,创造了一种全新的基于决策树的深度集成方法,为我们提供了决策树发展的另一种可能
    接下来我们打算通过3期的内容在深入理解决策树。包括:
    1) 了解决策树算法中参数及意义
    2) 基本的决策树算法: ID3, C4.5 和CART
    3) 高阶决策树算法:随机森林Random Forest、梯度提升树GBDT以及XGB/LGB
    我们将着重看一下每种算法的思想和优缺点
    下面我们通过一个案例在来熟悉一下决策树算法的基本流程。数据采用阿里天池的企鹅数据
    我们还是遵循一个完成的数据挖掘步骤:导入数据以及基本的数据查看清洗分析到可视化对数据分布有进一步和深入的了解在到最后的建模和训练。

    Step1:数据导入和基本的数据概览

    #导入库
    import pandas as pd
    import numpy as np
    import matplotlib.pyplot as plt
    import seaborn as sns
    %matplotlib inline
    
    plt.style.use('bmh') # 设置绘图风格为bmh
    #导入数据
    df = pd.read_csv('penguins_raw.csv')
    df.head()
    

    数据如下:

    image.png

    使用基本的shape/info/等函数查看数据集的基本概况:

    print(df.shape)
    print('*' * 20)
    df.info()
    print('*' * 20)
    df['Species'].value_counts()
    

    结果如下:


    image.png

    可以看到该数据集包含了8个变量,其中7个特征变量,分别是所在岛屿,嘴巴长度,嘴巴深度,脚蹼长度,身体体积,性别以及年龄1个目标分类变量。目标变量为企鹅的类别即企鹅类的三个亚属,分别是(Adélie, Chinstrap and Gentoo)。通过shape可以知道一共包含了344个样本。通过对种类做value_counts统计,可以知道Adelie Penguin样本最多,有152个。另外通过info函数看到有些特征有缺失。下面通过用平均值来对缺省值进行填充(数据清洗)。

    data = df[['Species','Culmen Length (mm)','Culmen Depth (mm)',
                'Flipper Length (mm)','Body Mass (g)']] #选择这4个数值特征
    
    # 下面对包含缺省值的列进行平均值填充
    for column in list(data.columns[data.isnull().sum() > 0]):
        mean_val = df[column].mean()
        data[column].fillna(mean_val, inplace=True)
    data.head()
    

    清洗后的效果如下:


    image.png

    对比之前的数据可以看到第四行的样本缺省值被处理了。

    Step 2. 数据可视化进一步了解数据分布

    2.1 特征与标签组合进行散点图

    首先通过一个简单的二元散点图和目标值的分布

    
    sns.pairplot(data = data, diag_kind='hist', hue = 'Species')
    
    penguni1.png

    2.2 单特征箱线图

    # 2.2 单个特征的箱线图
    f,ax = plt.subplots(2,2, figsize = (20,10))
    cols = ['Culmen Length (mm)','Culmen Depth (mm)', 'Flipper Length (mm)','Body Mass (g)']
    for i, col in enumerate(cols):
        sns.boxplot(x = 'Species', y = col, saturation=0.5, palette='pastel', data = data, ax = ax[i//2][i%2])
    
    penguni2.png

    上面通过一个循环语句搞定所有的特征变量,是个小技巧。特别是对于特征值较多的时候比较有用。 -结合2D散点图可以看出每个特征下,只可以区分一种,另外两种特征值都有重叠区域,但是可以先分开一类,在用另一个特征值分开另外一类。

    Step3. 决策树建模以及训练和预测

    from sklearn.model_selection import train_test_split
    from sklearn.tree import DecisionTreeClassifier
    from sklearn import tree
    from sklearn.metrics import accuracy_score,confusion_matrix
    
    # 划分特征变量X 和目标值y
    X = data.iloc[:, 1:5]
    y = data['Species']
    X_train, X_test, y_train, y_test = train_test_split(X, y, 
                                    test_size =0.2,  random_state = 2020) 
    

    创建模型,并采用默认值训练:

    clf = DecisionTreeClassifier()
    clf.fit(X_train,y_train)
    

    在决策树中,重要的参数如下:

    • criterion
      Criterion这个参数正是用来决定模型特征选择的计算方法的。sklearn提供了两种选择:
      选择”entropy“,使用信息熵(Entropy)
      选择”gini“,使用基尼系数,默认(Gini Impurity)
      信息熵和基尼系数我们会在下一期 ——基本的决策树算法 ID3, C4.5 和CART中详细介绍
    • random_state & splitter
      random_state用来设置分枝中的随机模式的参数,默认None,在高维度时随机性会表现更明显。splitter也是用来控制决策树中的随机选项的,有两种输入值,输入”best",决策树在分枝时虽然随机,但是还是会优先选择更重要的特征进行分枝(重要性可以通过属性feature_importances_查看),输入“random",决策树在分枝时会更加随机,树会因为含有更多的不必要信息而更深更大,并因这些不必要信息而降低对训练集的拟合。
    • max_depth
      限制树的最大深度,超过设定深度的树枝全部剪掉。这是用得最广泛的剪枝参数,在高维度低样本量时非常有效。决策树多生长一层,对样本量的需求会增加一倍,所以限制树深度能够有效地限制过拟合。
    • min_samples_leaf
      min_samples_leaf 限定,一个节点在分枝后的每个子节点都必须包含至少min_samples_leaf个训练样本,否则分枝就不会发生,或者,分枝会朝着满足每个子节点都包含min_samples_leaf个样本的方向去发生。一般搭配max_depth使用,在回归树中有神奇的效果,可以让模型变得更加平滑。这个参数的数量设置得太小会引起过拟合,设置得太大就会阻止模型学习数据。

    这里我们全部选择默认参数,进行训练,并预测结果

    train_predict = clf.predict(X_train)
    test_predict = clf.predict(X_test)
    
    train_res = accuracy_score(y_train, train_predict)
    test_res = accuracy_score(y_test, test_predict)
    
    print('The model accuracy on train set is: {:.4f}'.format(train_res))
    print('The model accuracy on test set is: {:.4f}'.format(test_res))
    
    >>> The model accuracy on train set is: 0.9964
    >>> The model accuracy on test set is: 0.9565
    

    可以看到模型训练后在训练集上取得0.99的高分成绩,在预测集上也有0.95以上的高分。这就好比一个同学平时做了大量的练习题,考试的时候如果题目直接从平时的练习题中抽测,分数一般会比较高。但是如果考试题是全新的未见过的,成绩就要差一点。同时在训练集中也没有获得100%的正确率,可以充分的说明模型是在学习这些特征和目标值之间的关系,而不是记忆。理解这一点很重要!

    可视化,看看模型是怎么分类的:


    penguni3.png

    当我们把这个树打印出来后,我们立马就可以联想到其实决策树和我们自己写一堆if-else一致!

    在可视化一下混淆矩阵:

    # 查看混淆矩阵
    confusion_matrix_res = confusion_matrix(test_predict, y_test)
    print('The confusion matrix result:\n',confusion_matrix_res)
    
    #利用热力图进行可视化
    plt.figure(figsize=(10,8))
    sns.heatmap(confusion_matrix_res, annot=True, cmap='Blues')
    
    plt.xlabel('Predicted labels', fontsize = 14)
    plt.ylabel('True labels', fontsize = 14)
    plt.title('Confusion Matrix HeatMap', fontsize = 15)
    

    结果如下:


    penguni4.png

    好了,本期内容到此结束,下一期我们具体思考一下ID3, C4.5以及CART的算法思想。其实不同的决策树学习算法只是它们选择特征的依据不同,决策树的生成过程都遵循同样的处理流程。

    我们要知道没有一个模型是万能的,每个模型都有其自身的局限性,没有哪个模型能做到通吃。这就需要我们学习不同的算法和模型,依据不同的场景和应用需求来选择合适的解法。这个问题的背后的根本原因是现实世界和需求的复杂性。需求的复杂性导致业务的复杂性,业务的复杂性决定了设计的复杂性。但是不管怎样,这些复杂事务最本质和核心的那一坨仍然是非常单纯和浅显的。

    这就是我们要学习不同模型的原因。每个模型都有它擅长的场景,选好了能做到事半功倍的效果。而深入理解每个模型的底层原理和架构是灵活运用的前提。

    相关文章

      网友评论

        本文标题:通过一个小案例熟悉决策树算法中的参数

        本文链接:https://www.haomeiwen.com/subject/sxsxhktx.html