决策树(二)——决策树的生成

说明:这篇博客是看李航老师的《统计学习方法》的笔记总结,博客中有很多内容是摘选自李航老师的《统计学习方法》一书,仅供学习交流使用。

决策树的生成

在上一篇博客决策树(一)——构建决策树中,我们已经讲述了决策树三步骤中的特征选择,今天我们首先来讲解一下决策树的生成。

决策树生成的基本思想是分割数据集。具体的做法就是尝试每一个特征,并衡量哪一个特征会给你带来最好的结果,然后,基于最优的特征分割数据集(由于最优特征可能有好几个值,所以我们也可能会得到多个子集)。第一次划分之后,数据集被向下传递到树的分支的下一个结点。在这个结点上,我们可以再次划分数据。即我们可以采用递归来处理数据集。

决策树生成的算法有ID3、C4.5等,我们先来讲解一下ID3算法。

ID3

ID3算法的核心是在决策树各个节点上应用信息增益准则选择特征,递归地构造决策树。

输入:训练数据集D,特征集A阈值ε

输出:决策树T

(1)若D中所有实例属于同一类 C k C_k Ck,则T为单结点树,并将类 C k C_k Ck作为该结点的类标记,返回T;

(2)若 A = ∅ A=∅ A=,则T为单结点树,并将D中实例数最大的类 C k C_k Ck作为该结点的类标记,返回T;

(3)否则,计算A中各特征对D的信息增益,选择信息增益最大的特征 A g A_g Ag

(4)如果 A g A_g Ag的信息增益小于阈值ε,则置T为单结点树,并将D中实例数最大的类 C k C_k Ck作为该结点的类标记,返回T;

(5)否则,对 A g A_g Ag的每一可能值 a i a_i ai,依 A g = a i A_g=a_i Ag=ai将D分割为若干非空子集 D i D_i Di,将 D i D_i Di中实例数最大的类最为标记,构建子节点,由结点及其子结点构成树T,返回T;

(6)对第i个子结点,以 D i D_i Di为训练集,以 A − { A g } A-\{A_g\} A{Ag}为特征集,递归地调用步(1)~(5),得到子树 T i T_i Ti,返回 T i T_i Ti

举例

其实在上一篇博客,我们通过对各特征计算其各自的信息增益已经知道第三个特征(有自己的房子)的信息增益最大,故其就是决策树的根节点;然后该特征取值有两个:是 or 否,故我们可以把数据集D分成两个子集 D 是 D_是 D D 否 D_否 D,那么数据集就该是这样的:(在选出最优特征后,我们需要删除最优特征的标签,及其在数据集中的值)

D 是 D_是 D

ID年龄有工作信贷情况类别
4青年一般
8中年
9中年非常好
10中年非常好
11老年非常好
12老年

根据表格可知,有自己的房子的类别均为,满足决策树算法的第一条,所以返回类标签

D 否 D_否 D

ID年龄有工作信贷情况类别
1青年一般
2青年
3青年
5青年一般
6中年一般
7中年
13老年
14老年非常好
15老年一般

子集 D 否 D_否 D就需要计算 g ( D 否 , A ) g(D_否,A) g(DA)来比较哪一个特征更适合做子集 D 否 D_否 D的根结点了,下面咱们我就带着大家简单的计算一下。

假设 A 1 A_1 A1表示特征年龄, A 2 A_2 A2表示特征有, A 3 A_3 A3表示特征信贷情况
g ( D 否 , A 1 ) = H ( D 否 ) − H ( D 否 , A 1 ) = − 6 9 l o g 2 6 9 − 3 9 l o g 2 3 9 − [ 4 9 ( − 3 4 l o g 2 3 4 − 1 4 l o g 2 1 4 ) + 2 9 ∗ 0 + 3 9 ( − 2 3 l o g 2 2 3 − 1 3 l o g 2 1 3 ) ] = 0.918 − ( 0.361 + 0 + 0.306 ) = 0.251 \begin{aligned} g(D_否,A_1)&=H(D_否)-H(D_否,A_1) \\ &=-\frac{6}{9}log_2\frac{6}{9}-\frac{3}{9}log_2\frac{3}{9}-[\frac{4}{9}(-\frac{3}{4}log_2\frac{3}{4}-\frac{1}{4}log_2\frac{1}{4})+\frac{2}{9}*0+\frac{3}{9}(-\frac{2}{3}log_2\frac{2}{3}-\frac{1}{3}log_2\frac{1}{3})] \\ &=0.918-(0.361+0+0.306) \\ &=0.251 \end{aligned} g(D,A1)=H(D)H(D,A1)=96log29693log293[94(43log24341log241)+920+93(32log23231log231)]=0.918(0.361+0+0.306)=0.251
其他特征同理。

代码实现

from math import log
import operator

def createDataSet():
    # 数据集
    dataSet=[[0, 0, 0, 0, 'no'],
            [0, 0, 0, 1, 'no'],
            [0, 1, 0, 1, 'yes'],
            [0, 1, 1, 0, 'yes'],
            [0, 0, 0, 0, 'no'],
            [1, 0, 0, 0, 'no'],
            [1, 0, 0, 1, 'no'],
            [1, 1, 1, 1, 'yes'],
            [1, 0, 1, 2, 'yes'],
            [1, 0, 1, 2, 'yes'],
            [2, 0, 1, 2, 'yes'],
            [2, 0, 1, 1, 'yes'],
            [2, 1, 0, 1, 'yes'],
            [2, 1, 0, 2, 'yes'],
            [2, 0, 0, 0, 'no']]
    #分类属性
    labels=['年龄','有工作','有自己的房子','信贷情况']
    #返回数据集和分类属性
    return dataSet,labels

#香农熵(经验熵)
def calcShannonEnt(dataSet):
    #数据集行数
    numEntries=len(dataSet)
    #保存类标签出现次数的字典
    labelCounts={}
    #对每组特征向量进行统计
    for featVec in dataSet:
        currentLabel=featVec[-1]                     #类标签
        if currentLabel not in labelCounts.keys():   #如果标签没有放入统计次数的字典,添加进去
            labelCounts[currentLabel]=0
        labelCounts[currentLabel]+=1                 

    shannonEnt=0.0                                   
    #计算经验熵
    for key in labelCounts:
        prob=float(labelCounts[key])/numEntries      
        shannonEnt-=prob*log(prob,2)                
    return shannonEnt                                #返回经验熵

#分割数据集
def splitDataSet(dataSet,axis,value):
    retDataSet=[]
    #遍历数据集
    for featVec in dataSet:
        if featVec[axis]==value:
            #去掉axis特征
            reduceFeatVec=featVec[:axis]
            reduceFeatVec.extend(featVec[axis+1:])
            #将符合条件的添加到返回的数据集
            retDataSet.append(reduceFeatVec)
    return retDataSet
    
#求实例数最多的类
def majorityCnt(classList):
    classCount={}
    #统计classList中每个元素出现的次数
    for vote in classList:
        if vote not in classCount.keys():
            classCount[vote]=0
        classCount[vote]+=1
    #根据字典的值降序排列
    sortedClassCount=sorted(classCount.items(),key=operator.itemgetter(1),reverse=True)
    return sortedClassCount[0][0]

#选择最优特征(依据:信息增益 or 信息增益比)
def chooseBestFeatureToSplit(dataSet):
    #特征数量
    numFeatures = len(dataSet[0]) - 1
    baseEntropy = calcShannonEnt(dataSet)
    #信息增益
    bestInfoGain = 0.0
    #最优特征的索引值
    bestFeature = -1
    #遍历所有特征
    for i in range(numFeatures):
        # 获取dataSet的第i个所有特征
        featList = [example[i] for example in dataSet]
        #创建set集合{},元素不可重复
        uniqueVals = set(featList)
        #经验条件熵
        newEntropy = 0.0
        #计算信息增益
        for value in uniqueVals:
            #subDataSet划分后的子集
            subDataSet = splitDataSet(dataSet, i, value)
            prob = len(subDataSet) / float(len(dataSet))
            #根据公式计算经验条件熵
            newEntropy += prob * calcShannonEnt((subDataSet))
        #信息增益
        infoGain = baseEntropy - newEntropy
        #打印每个特征的信息增益
        print("第%d个特征的增益为%.3f" % (i, infoGain))
        #选择信息增益最大的特征,并存储其索引
        if (infoGain > bestInfoGain):
            bestInfoGain = infoGain
            bestFeature = i
    return bestFeature

#创建决策树
def createTree(dataSet,labels,featLabels):
    #读取类标签
    classList=[example[-1] for example in dataSet]
    #如果D中所有实例同属于一个类
    if classList.count(classList[0])==len(classList):
        return classList[0]
    #遍历完所有特征时返回出现次数最多的类标签
    if len(dataSet[0])==1:
        return majorityCnt(classList)
    #选择最优特征
    bestFeat=chooseBestFeatureToSplit(dataSet)
    #最优特征的标签
    bestFeatLabel=labels[bestFeat]
    featLabels.append(bestFeatLabel)
    #根据最优特征的标签生成树
    myTree={bestFeatLabel:{}}
    #删除已经使用的特征标签
    del(labels[bestFeat])
    #得到训练集中所有最优特征的属性值
    featValues=[example[bestFeat] for example in dataSet]
    #去掉重复的属性值
    uniqueVls=set(featValues)
    #遍历特征,创建决策树
    for value in uniqueVls:
        myTree[bestFeatLabel][value]=createTree(splitDataSet(dataSet,bestFeat,value),
                                               labels,featLabels)
    return myTree

if __name__=='__main__':
    dataSet,labels=createDataSet()
    featLabels=[]
    myTree=createTree(dataSet,labels,featLabels)
    print(myTree)
第0个特征的增益为0.083
第1个特征的增益为0.324
第2个特征的增益为0.420
第3个特征的增益为0.363
第0个特征的增益为0.252
第1个特征的增益为0.918
第2个特征的增益为0.474
{'有自己的房子': {0: {'有工作': {0: 'no', 1: 'yes'}}, 1: 'yes'}}

img

C4.5

C4.5同ID3很是相似,只是在选择最优特征时使用的不是信息增益,而是信息增益比,故此处不多赘述。

代码实现

C4.5算法的实现可以参考ID3,我这里简单的把需要修改的部分展示出来。

大家都知道信息增益比的公式是 g R ( D , A ) = g ( D , A ) H A ( D ) g_R(D,A)=\frac{g(D,A)}{H_A(D)} gR(D,A)=HA(D)g(D,A),这里就简单地带大家计算一下 H A ( D ) H_A(D) HA(D)

我们之前就已经计算过第一个特征的信息增益了,这里我们就直接拿来用。

g ( D , A 1 ) = 0.083 g(D,A_1)=0.083 g(D,A1)=0.083
H A 1 ( D ) = − ∑ i = 1 n ∣ D i ∣ ∣ D ∣ l o g 2 ∣ D i ∣ ∣ D ∣ = − 5 15 l o g 2 5 15 − 5 15 l o g 2 5 15 − 5 15 l o g 2 5 15 = − l o g 2 5 15 = 1.585 \begin{aligned} H_{A_1}(D)&=-\sum_{i=1}^n\frac{|D_i|}{|D|}log_2\frac{|D_i|}{|D|} \\ &=-\frac{5}{15}log_2\frac{5}{15}-\frac{5}{15}log_2\frac{5}{15}-\frac{5}{15}log_2\frac{5}{15} \\ &=-log_2\frac{5}{15} \\ &=1.585 \end{aligned} HA1(D)=i=1nDDilog2DDi=155log2155155log2155155log2155=log2155=1.585
g R ( D , A ) = g ( D , A ) H A ( D ) = 0.083 1.585 ≈ 0.052 g_R(D,A)=\frac{g(D,A)}{H_A(D)}=\frac{0.083}{1.585}≈0.052 gR(D,A)=HA(D)g(D,A)=1.5850.0830.052

下面的calcAShannonEnt()函数就是对 H A ( D ) H_A(D) HA(D)的计算。

def calcAShannonEnt(dataSet,i):
    #返回数据集行数
    numEntries=len(dataSet)
    #保存每个标签(label)出现次数的字典
    labelCounts={}
    #对每组特征向量进行统计
    for featVec in dataSet:
        currentLabel=featVec[i]                     #提取标签信息
        if currentLabel not in labelCounts.keys():   #如果标签没有放入统计次数的字典,添加进去
            labelCounts[currentLabel]=0
        labelCounts[currentLabel]+=1                 #label计数

    shannonEnt=0.0                                   #经验熵
    #计算经验熵
    for key in labelCounts:
        prob=float(labelCounts[key])/numEntries      #选择该标签的概率
        shannonEnt-=prob*log(prob,2)                 #利用公式计算
    return shannonEnt

接下来需要改的就是chooseBestFeatureToSplit()函数,该函数主要是计算了信息增益 g ( D , A ) g(D,A) g(D,A)与特征A数据集经验熵 H A ( D ) H_A(D) HA(D)之间的比值。

def chooseBestFeatureToSplit(dataSet):
    #特征数量
    numFeatures = len(dataSet[0]) - 1
    #计数数据集的香农熵
    baseEntropy = calcShannonEnt(dataSet)
    #信息增益
    bestInfoGainRate = 0.0
    #最优特征的索引值
    bestFeature = -1
    #遍历所有特征
    for i in range(numFeatures):
        # 获取dataSet的第i个所有特征
        featList = [example[i] for example in dataSet]
        #创建set集合{},元素不可重复
        uniqueVals = set(featList)
        #经验条件熵
        newEntropy = 0.0
        #计算信息增益
        for value in uniqueVals:
            #subDataSet划分后的子集
            subDataSet = splitDataSet(dataSet, i, value)
            #计算子集的概率
            prob = len(subDataSet) / float(len(dataSet))
            #根据公式计算经验条件熵
            newEntropy += prob * calcShannonEnt((subDataSet))
        #信息增益
        infoGain = baseEntropy - newEntropy
        if calcAShannonEnt(dataSet,i) == 0:
            continue
        #信息增益
        infoGain = baseEntropy - newEntropy
        #print("第%d个特征的增益比为%.3f" % (i, infoGain))
        if calcAShannonEnt(dataSet,i) == 0:
            continue
        #print("第%d个特征的增益比为%.3f" % (i, calcAShannonEnt(dataSet,i)))
        #信息增益比
        infoGainRate = infoGain / calcAShannonEnt(dataSet,i)
        print("第%d个特征的增益比为%.3f" % (i, infoGainRate))
        #计算信息增益
        if (infoGainRate > bestInfoGainRate):
            #更新信息增益,找到最大的信息增益
            bestInfoGainRate = infoGainRate
            #记录信息增益最大的特征的索引值
            bestFeature = i
            #返回信息增益最大特征的索引值
    return bestFeature
第0个特征的增益比为0.052
第1个特征的增益比为0.352
第2个特征的增益比为0.433
第3个特征的增益比为0.232
第0个特征的增益比为0.164
第1个特征的增益比为1.000
第2个特征的增益比为0.340
{'有自己的房子': {0: {'有工作': {0: 'no', 1: 'yes'}}, 1: 'yes'}}

cart生成算法

cart模型分回归树与分类树两种,而这里只讲解下分类树。

分类树用基尼指数选择最优特征,同时决定该特征的最有二值切分点。

基尼指数:分类问题中,假设有K个类,样本点属于第k类的概率为 p k p_k pk,则概率分布的基尼指数定义为
G i n i ( p ) = ∑ k = 1 K p k ( 1 − p k ) = 1 − ∑ k = 1 K p k 2 Gini(p)=\sum_{k=1}^Kp_k(1-p_k)=1-\sum_{k=1}^Kp_k^2 Gini(p)=k=1Kpk(1pk)=1k=1Kpk2
对于二类分类问题,若样本点属于第1个类的概率是p,则概率分布的基尼指数为
G i n i ( p ) = 2 p ( 1 − p ) Gini(p)=2p(1-p) Gini(p)=2p(1p)
对于给定样本集合D,其基尼指数为
G i n i ( D ) = 1 − ∑ k = 1 K ( ∣ C k ∣ ∣ D ∣ ) 2 Gini(D)=1-\sum_{k=1}^K(\frac{|C_k|}{|D|})^2 Gini(D)=1k=1K(DCk)2
如果样本集合D根据特征A是否取某一可能值a被分割为 D 1 D_1 D1 D 2 D_2 D2两部分,即
D 1 = { ( x , y ) ∈ D ∣ A ( x ) = a } ,   D 2 = D − D 1 D_1=\{(x,y)∈D|A(x)=a\}, \ D_2=D-D_1 D1={(x,y)DA(x)=a}, D2=DD1
则在特征A的条件下,集合D的基尼指数定义为
G i n i ( D , A ) = ∣ D 1 ∣ ∣ D 2 ∣ G i n i ( D 1 ) + ∣ D 2 ∣ ∣ D ∣ G i n i ( D 2 ) Gini(D,A)=\frac{|D_1|}{|D_2|}Gini(D_1)+\frac{|D_2|}{|D|}Gini(D_2) Gini(D,A)=D2D1Gini(D1)+DD2Gini(D2)
注:基尼指数Gini(D)表示集合D的不确定性,基尼指数Gini(D,A)表示经A=a分割后集合D的不确定性。

生成算法

输入:训练数据集D,停止计算的条件;

输出:CART决策树

根据训练数据集,从根结点开始,递归地对每个结点进行以下操作,构建二叉决策树。

(1)设结点的训练数据集为D,计算现有特征对该数据集的基尼指数。此时,对每一个特征A,对其可能取得每个值a,根据样本点对A=a的测试为“是”或“否”将D分割成 D 1 D_1 D1 D 2 D_2 D2两部分,利用上述最后一个公式计算A=a时的基尼指数。

(2)在所有可能的特征A以及他们所有可能的切分点a中,选择基尼指数最小的特征及其对应的切分点作为最优特征与最优切分点。依最优特征与最优切分点,从现结点生成两个子结点,将训练数据集依特征分配到两个子节点中。

(3)对两个子结点递归调用(1),(2),直到满足条件。

(4)生成cart决策树。

def createDataSet():
    # 数据集
    dataSet=[[0, 0, 0, 0, 'no'],
            [0, 0, 0, 1, 'no'],
            [0, 1, 0, 1, 'yes'],
            [0, 1, 1, 0, 'yes'],
            [0, 0, 0, 0, 'no'],
            [1, 0, 0, 0, 'no'],
            [1, 0, 0, 1, 'no'],
            [1, 1, 1, 1, 'yes'],
            [1, 0, 1, 2, 'yes'],
            [1, 0, 1, 2, 'yes'],
            [2, 0, 1, 2, 'yes'],
            [2, 0, 1, 1, 'yes'],
            [2, 1, 0, 1, 'yes'],
            [2, 1, 0, 2, 'yes'],
            [2, 0, 0, 0, 'no']]
    #分类属性
    labels=['年龄','有工作','有自己的房子','信贷情况']
    #返回数据集和分类属性
    return dataSet,labels

#计算基尼指数Gini(D)
def calcGini(dataSet):
    #返回数据集行数
    numEntries=len(dataSet)
    #保存每个标签(label)出现次数的字典
    labelCounts={}
    #对每组特征向量进行统计
    for featVec in dataSet:
        currentLabel=featVec[-1]                     #提取标签信息
        if currentLabel not in labelCounts.keys():   #如果标签没有放入统计次数的字典,添加进去
            labelCounts[currentLabel]=0
        labelCounts[currentLabel]+=1                 

    gini=1.0                                  
    #计算基尼指数
    for key in labelCounts:
        prob=float(labelCounts[key])/numEntries      
        gini-=prob**2                
    return gini  

def splitDataSet(dataSet,axis,value):
    #创建返回的数据集列表
    retDataSet=[]
    #遍历数据集
    for featVec in dataSet:
        if featVec[axis]==value:
            #去掉axis特征
            reduceFeatVec=featVec[:axis]
            #将符合条件的添加到返回的数据集
            reduceFeatVec.extend(featVec[axis+1:])
            retDataSet.append(reduceFeatVec)
    #返回划分后的数据集
    return retDataSet
#获取特征其他样本的子集
def splitOtherDataSetByValue(dataSet,axis,value):
    #创建返回的数据集列表
    retDataSet=[]
    #遍历数据集
    for featVec in dataSet:
        if featVec[axis]!=value:
            #去掉axis特征
            reduceFeatVec=featVec[:axis]
            #将符合条件的添加到返回的数据集
            reduceFeatVec.extend(featVec[axis+1:])
            retDataSet.append(reduceFeatVec)
    #返回划分后的数据集
    return retDataSet
def binaryZationDataSet(bestFeature,bestSplitValue,dataSet):
        # 求特征标签数
        featList = [example[bestFeature] for example in dataSet]
        uniqueValues = set(featList)

        # 特征标签输超过2,对数据集进行二值划分
        if len(uniqueValues) >= 2:
                for i in range(len(dataSet)):
                        if dataSet[i][bestFeature] == bestSplitValue: # 不做处理
                                pass
                        else:
                                dataSet[i][bestFeature] = '其他'

def chooseBestFeatureToSplit(dataSet):
    #特征数量
    numFeatures = len(dataSet[0]) - 1
    #初始化最优基尼指数值
    bestGiniIndex = 1000000.0
    bestSplictValue =-1
    #最优特征的索引值
    bestFeature = -1
    #遍历所有特征
    for i in range(numFeatures):
        # 获取dataSet的第i个所有特征
        featList = [example[i] for example in dataSet]
        #创建set集合{},元素不可重复
        uniqueVals = set(featList)
        bestGiniCut = 1000000.0
        bestGiniCutValue =-1
        giniValue = 0.0
        for value in uniqueVals:
            subDataSet1 = splitDataSet(dataSet, i, value)
            prob = len(subDataSet1) / float(len(dataSet))
            subDataSet2 = splitOtherDataSetByValue(dataSet, i, value) 
            prob_ = len(subDataSet2) / float(len(dataSet))
            #根据公式计算基尼指数
            giniValue = prob * calcGini(subDataSet1) + prob_ * calcGini(subDataSet2)
#             if(len(uniqueVals)==2):
#                 print("第%d个特征的基尼指数为%.2f" % (i, gini_A))
#                 break
#             else:
#                 print("第%d个特征第%d个样本的基尼指数为%.2f" % (i, value, gini_A))
            #找出最优切分点
            if (giniValue < bestGiniCut):
                bestGiniCut = giniValue
                bestGiniCutValue = value
                
        # 选择最优特征向量
        GiniIndex = bestGiniCut
        if GiniIndex < bestGiniIndex:
            bestGiniIndex = GiniIndex
            bestSplictValue = bestGiniCutValue
            bestFeature = i
            
    # 若当前结点的划分结点特征中的标签超过3个,则将其以之前记录的划分点为界进行二值化处理
    binaryZationDataSet(bestFeature,bestSplictValue,dataSet)
    return bestFeature

def majorityCnt(classList):
    classCount={}
    #统计classList中每个元素出现的次数
    for vote in classList:
        if vote not in classCount.keys():
            classCount[vote]=0
        classCount[vote]+=1
    #根据字典的值降序排列
    sortedClassCount=sorted(classCount.items(),key=operator.itemgetter(1),reverse=True)
    return sortedClassCount[0][0]

def createTree(dataSet,labels,featLabels):
    classList=[example[-1] for example in dataSet]
    #如果D中所有实例同属于一个类
    if classList.count(classList[0])==len(classList):
        return classList[0]
    #遍历完所有特征时返回出现次数最多的类标签
    if len(dataSet[0])==1:
        return majorityCnt(classList)
    #选择最优特征
    bestFeat=chooseBestFeatureToSplit(dataSet)
    #最优特征的标签
    bestFeatLabel=labels[bestFeat]
    featLabels.append(bestFeatLabel)
    #根据最优特征的标签生成树
    myTree={bestFeatLabel:{}}
    #删除已经使用的特征标签
    del(labels[bestFeat])
    #得到训练集中所有最优特征的属性值
    featValues=[example[bestFeat] for example in dataSet]
    #去掉重复的属性值
    uniqueVls=set(featValues)
    #遍历特征,创建决策树
    for value in uniqueVls:
        myTree[bestFeatLabel][value]=createTree(splitDataSet(dataSet,bestFeat,value),
                                               labels,featLabels)
    return myTree

if __name__=='__main__':
    dataSet,labels=createDataSet()
    featLabels=[]
    myTree=createTree(dataSet,labels,featLabels)
    print(myTree)
{'有自己的房子': {0: {'有工作': {0: 'no', '其他': 'yes'}}, '其他': 'yes'}}

决策树的剪枝

决策树生成算法递归地产生决策树,直到不能继续下去为止。这样产生的树往往对训练数据的分类很准确,但对未知的测试数据的分类却没有那么准确,即出现过拟合现象。解决这个问题的办法是考虑决策树复杂度,对已产生的决策树进行简化。

在决策时学习中将已生成的树进行简化的过程称为剪枝(pruning)。具体地,剪枝从已生成的书上裁掉一些子树或叶节点,并将其根节点或父节点作为新的叶节点,从而简化分类树模型。

在《统计学习方法》中介绍了一种简单的决策树学习的剪枝算法,但是由于其内容我尚存一些疑问,故暂时空着。

  • 3
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值