sklearn中的决策树-分类树:重要参数

分类树

  • sklearn.tree.DecisionTreeClassifier

    python 复制代码
    sklearn.tree.DecisionTreeClassifier (criterion='gini' # 不纯度计算方法
                                         , splitter='best' # best & random
                                         , max_depth=None # 树最大深度
                                         , min_samples_split=2 # 当前节点可划分最少样本数
                                         , min_samples_leaf=1 # 子节点最少样本数
                                         , min_weight_fraction_leaf=0.0
                                         , max_features=None
                                         , random_state=None
                                         , max_leaf_nodes=None
                                         , min_impurity_decrease=0.0
                                         , min_impurity_split=None
                                         , class_weight=None
                                         , presort=False
                                        )

重要参数

criterion
  • criterion这个参数正是用来决定不纯度的计算方法的。

    sklearn提供了两种选择:

    1. 输入"entropy",使用信息熵(Entropy),sklearn实际计算的是基于信息熵的信息增益(Information Gain),即父节点的信息熵和子节点的信息熵之差。
    2. 输入"gini",使用基尼系数(Gini Impurity)

    E n t r o p y ( t ) = − ∑ i = 0 c − 1 p ( i ∣ t ) log ⁡ 2 p ( i ∣ t ) Entropy(t) = - \sum \limits_{i=0}^{c-1} p(i|t)\log{_2}p(i|t) Entropy(t)=−i=0∑c−1p(i∣t)log2p(i∣t)

    G i n i ( t ) = 1 − ∑ i = 0 c − 1 p ( i ∣ t ) 2 Gini(t) = 1 - \sum_{i=0}^{c-1}p(i|t)^2 Gini(t)=1−i=0∑c−1p(i∣t)2

    其中t代表给定的节点,i代表标签的任意分类, p ( i ∣ t ) p(i|t) p(i∣t) 代表标签分类i在节点t上所占的比例。注意,当使用信息熵 时,sklearn实际计算的是基于信息熵的信息增益(Information Gain),即父节点的信息熵和子节点的信息熵之差。 比起基尼系数,信息熵对不纯度更加敏感,对不纯度的惩罚最强。但是在实际使用中,信息熵和基尼系数的效果基 本相同。信息熵的计算比基尼系数缓慢一些,因为基尼系数的计算不涉及对数。另外,因为信息熵对不纯度更加敏 感,所以信息熵作为指标时,决策树的生长会更加"精细",因此对于高维数据或者噪音很多的数据,信息熵很容易 过拟合,基尼系数在这种情况下效果往往比较好。当模型拟合程度不足的时候,即当模型在训练集和测试集上都表 现不太好的时候,使用信息熵。当然,这些不是绝对的。

    参数 criterion
    如何影响模型? 确定不纯度的计算方法,帮忙找出最佳节点和最佳分枝,不纯度越低,决策树对训练集 的拟合越好
    可能的输入有哪 些? 不填默认基尼系数,填写gini使用基尼系数,填写entropy使用信息增益
    怎样选取参数? 通常就使用基尼系数 数据维度很大,噪音很大时使用基尼系数 维度低,数据比较清晰的时候,信息熵和基尼系数没区别 当决策树的拟合程度不够的时候,使用信息熵,两个都试试不好就换另一个
    python 复制代码
    # -*- coding: utf-8 -*-
    
    """
    **************************************************
    @author:   Ying                                      
    @software: PyCharm                       
    @file: 分类树_criterion.py
    @time: 2021-08-20 16:13                          
    **************************************************
    """
    from sklearn import tree
    from sklearn.datasets import load_wine
    from sklearn.model_selection import train_test_split
    import pandas as pd
    import graphviz
    
    # 加载数据
    wine = load_wine()
    data = pd.DataFrame(wine.data, columns=wine.feature_names)  # X
    target = pd.DataFrame(wine.target)  # y
    
    # 划分训练测试集
    X_train, X_test, y_train, y_test = train_test_split(data, target, test_size=0.3)
    
    # 两种criterion
    
    for criterion_ in ['entropy', 'gini']:
        clf = tree.DecisionTreeClassifier(criterion=criterion_)
        clf.fit(X_train, y_train)
        score = clf.score(X_test, y_test)  # 返回预测的准确度
        print(f'criterion:{criterion_} \t accurancy : {score}')
    
        # 保存决策树图
        feature_name = ['酒精', '苹果酸', '灰', '灰的碱性', '镁', '总酚', '类黄酮', '非黄烷类酚类',
                        '花青素', '颜色强度', '色调', 'od280/od315稀释葡萄酒', '脯氨酸']
    
        dot_data = tree.export_graphviz(clf
                                        , feature_names=feature_name
                                        , class_names=["琴酒", "雪莉", "贝尔摩德"]
                                        , filled=True  # 填充颜色
                                        , rounded=True  # 圆角
                                        )
        graph = graphviz.Source(dot_data)
    
        graph.render(view=True, format="pdf", filename=f"decisiontree_pdf_{criterion_}")
    
        # 特征重要性
        feature_importances = clf.feature_importances_
        for i in [*zip(feature_name, feature_importances)]:
            print(i)
        print()

    python 复制代码
    """输出如下"""
    
    criterion:entropy 	 accurancy : 0.8703703703703703
    ('酒精', 0.0)
    ('苹果酸', 0.0)
    ('灰', 0.0)
    ('灰的碱性', 0.02494246008989065)
    ('镁', 0.0)
    ('总酚', 0.0)
    ('类黄酮', 0.3296114164674079)
    ('非黄烷类酚类', 0.0)
    ('花青素', 0.0)
    ('颜色强度', 0.14329965511242485)
    ('色调', 0.0)
    ('od280/od315稀释葡萄酒', 0.0)
    ('脯氨酸', 0.5021464683302767)
    
    criterion:gini 	 accurancy : 0.8148148148148148
    ('酒精', 0.0)
    ('苹果酸', 0.0)
    ('灰', 0.0)
    ('灰的碱性', 0.0)
    ('镁', 0.04779989924874613)
    ('总酚', 0.06725255711062922)
    ('类黄酮', 0.3230308396876504)
    ('非黄烷类酚类', 0.0)
    ('花青素', 0.0235378291755189)
    ('颜色强度', 0.0)
    ('色调', 0.0)
    ('od280/od315稀释葡萄酒', 0.0878400745934749)
    ('脯氨酸', 0.45053880018398057)
  • 回到模型步骤,每次运行score会在某个值附近 波动,引起每次画出来的每一棵树都不一样。它为什么会不稳定呢?如果使用其他数据集,它还会不稳定吗?

    无论决策树模型如何进化,在分枝上的本质都还是追求某个不纯度相关的指标的优化,而正如我 们提到的,不纯度是基于节点来计算的,也就是说,决策树在建树时,是靠优化节点来追求一棵优化的树,但最优 的节点能够保证最优的树吗?集成算法被用来解决这个问题:sklearn表示,既然一棵树不能保证最优,那就建更 多的不同的树,然后从中取最好的。怎样从一组数据集中建不同的树?在每次分枝时,不从使用全部特征,而是随 机选取一部分特征,从中选取不纯度相关指标最优的作为分枝用的节点。这样,每次生成的树也就不同了。

random_state&spliter
  • random_state用来设置分枝中的随机模式的参数,默认None,在高维度时随机性会表现更明显,低维度的数据 (比如鸢尾花数据集),随机性几乎不会显现。输入任意整数,会一直长出同一棵树,让模型稳定下来。

  • splitter也是用来控制决策树中的随机选项的,有两种输入值:

    1. best
    2. random

    输入"best",决策树在分枝时虽然随机,但是还是会 优先选择更重要的特征进行分枝(重要性可以通过属性feature_importances_查看)

    输入"random",决策树在 分枝时会更加随机,树会因为含有更多的不必要信息而更深更大,并因这些不必要信息而降低对训练集的拟合。这 也是防止过拟合的一种方式。当你预测到你的模型会过拟合,用这两个参数来帮助你降低树建成之后过拟合的可能 性。当然,树一旦建成,我们依然是使用剪枝参数来防止过拟合。

    python 复制代码
    # -*- coding: utf-8 -*-
    
    """
    **************************************************
    @author:   Ying                                      
    @software: PyCharm                       
    @file: 2、分类树_random_state&spliter.py
    @time: 2021-08-20 16:58                          
    **************************************************
    """
    
    from sklearn import tree
    from sklearn.datasets import load_wine
    from sklearn.model_selection import train_test_split
    import pandas as pd
    import graphviz
    
    # 加载数据
    wine = load_wine()
    data = pd.DataFrame(wine.data, columns=wine.feature_names)  # X
    target = pd.DataFrame(wine.target)  # y
    
    # 划分训练测试集
    X_train, X_test, y_train, y_test = train_test_split(data, target, test_size=0.3)
    
    clf = tree.DecisionTreeClassifier(criterion='gini'
                                      , random_state=30
                                      , splitter='best')
    
    clf.fit(X_train, y_train)
    score = clf.score(X_test, y_test)  # 返回预测的准确度
    
    # 保存决策树图
    feature_name = ['酒精', '苹果酸', '灰', '灰的碱性', '镁', '总酚', '类黄酮', '非黄烷类酚类',
                    '花青素', '颜色强度', '色调', 'od280/od315稀释葡萄酒', '脯氨酸']
    
    dot_data = tree.export_graphviz(clf
                                    , feature_names=feature_name
                                    , class_names=["琴酒", "雪莉", "贝尔摩德"]
                                    , filled=True  # 填充颜色
                                    , rounded=True  # 圆角
                                    )
    graph = graphviz.Source(dot_data)
    
    graph.render(view=True, format="pdf", filename="decisiontree_pdf")
    
    # 特征重要性
    feature_importances = clf.feature_importances_
    
    a = pd.DataFrame([*zip(feature_name, feature_importances)])
    a.columns = ['feature', 'importance']
    a.sort_values('importance', ascending=False, inplace=True)
    print(a)
相关推荐
计算机软件程序设计33 分钟前
深度学习在图像识别中的应用-以花卉分类系统为例
人工智能·深度学习·分类
lcw_lance6 小时前
人工智能(AI)的不同维度分类
人工智能·分类·数据挖掘
huaqianzkh9 小时前
理解构件的3种分类方法
人工智能·分类·数据挖掘
ww180001 天前
多目标粒子群优化算法-MOPSO-(机器人路径规划/多目标信号处理(图像/音频))
人工智能·算法·分类·信号处理
xiao5kou4chang6kai42 天前
基于python深度学习遥感影像地物分类与目标识别、分割实践技术应用
python·深度学习·分类
zhengyawen6662 天前
深度学习之图像分类(一)
人工智能·深度学习·分类
无极工作室(网络安全)2 天前
机器学习小项目之鸢尾花分类
人工智能·机器学习·分类
程序员JerrySUN2 天前
树莓派 4B:AI 物联网完整部署方案
linux·人工智能·嵌入式硬件·物联网·分类·数据挖掘
de之梦-御风3 天前
【OpenCV】OpenCV 中各模块及其算子的详细分类
人工智能·opencv·分类