博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
决策树之C4.5算法
阅读量:5155 次
发布时间:2019-06-13

本文共 5875 字,大约阅读时间需要 19 分钟。

决策树之C4.5算法

一、C4.5算法概述

  C4.5算法是最常用的决策树算法,因为它继承了ID3算法的所有优点并对ID3算法进行了改进和补充。

  改进有如下几个要点:

  1. 用信息增益率来选择属性,克服了ID3算法中信息增益选择属性时偏向选择取值多的属性的不足。

  C4.5算法选择决策属性的度量标准是增益比率gain ratio(Quinlan 1986)。增益比率度量是用前面的增益度量Gain(S,A)和分裂信息度量Splitlnformation(S,A)来共同定义的。为防遗忘,在此贴出信息熵和和信息增益的计算公式,如下所示:

 

 

由此,得出增益比率的公式如下:

其中,分裂信息度量被定义为(分裂信息用来衡量属性分裂数据的广度和均匀):

其中S1到Sc是c个值的属性A分割S而形成的c个样例子集。注意分裂信息实际上就是S关于属性A的各值的熵。

还是以一个典型被引用过多次的训练数据集D为例,来说明C4.5算法如何计算信息增益率并选择决策节点。

 

  上面的训练集有4个属性,即属性集合A={OUTLOOK, TEMPERATURE, HUMIDITY, WINDY};而类标签有2个,即类标签集合C={Yes, No},分别表示适合户外运动和不适合户外运动,其实是一个二分类问题。

我们已经计算过信息增益,这里直接列出来,如下所示:

数据集D包含14个训练样本,其中属于类别“Yes”的有9个,属于类别“No”的有5个,则计算其信息熵:Info(D) = -9/14 * log2(9/14) - 5/14 * log2(5/14) = 0.940

下面对属性集中每个属性分别计算信息熵,如下所示:

  (1)

Info(OUTLOOK) = 5/14 * [- 2/5 * log2(2/5) – 3/5 * log2(3/5)] + 4/14 * [ - 4/4 * log2(4/4) - 0/4 * log2(0/4)] + 5/14 * [ - 3/5 * log2(3/5) – 2/5 * log2(2/5)] = 0.694

  (2)

Info(TEMPERATURE) = 4/14 * [- 2/4 * log2(2/4) – 2/4 * log2(2/4)] + 6/14 * [ - 4/6 * log2(4/6) - 2/6 * log2(2/6)] + 4/14 * [ - 3/4 * log2(3/4) – 1/4 * log2(1/4)] = 0.911

  (3)

Info(HUMIDITY) = 7/14 * [- 3/7 * log2(3/7) – 4/7 * log2(4/7)] + 7/14 * [ - 6/7 * log2(6/7) - 1/7 * log2(1/7)] = 0.789

  (4)

Info(WINDY) = 6/14 * [- 3/6 * log2(3/6) – 3/6 * log2(3/6)] + 8/14 * [ - 6/8 * log2(6/8) - 2/8 * log2(2/8)] = 0.892

根据上面的数据,我们可以计算各属性的信息增益值,计算如下所示:

  (1)Gain(OUTLOOK) = Info(D) - Info(OUTLOOK) = 0.940 - 0.694 = 0.246

  (2)Gain(TEMPERATURE) = Info(D) - Info(TEMPERATURE) = 0.940 - 0.911 = 0.029

  (3)Gain(HUMIDITY) = Info(D) - Info(HUMIDITY) = 0.940 - 0.789 = 0.151

  (4)Gain(WINDY) = Info(D) - Info(WINDY) = 0.940 - 0.892 = 0.048

接下来,我们计算分裂信息度量H(V):

OUTLOOK属性

属性OUTLOOK有3个取值,其中Sunny有5个样本、Rainy有5个样本、Overcast有4个样本,则

Split(OUTLOOK) = - 5/14 * log2(5/14) - 5/14 * log2(5/14) - 4/14 * log2(4/14) = 1.577406282852345

TEMPERATURE属性

属性TEMPERATURE有3个取值,其中Hot有4个样本、Mild有6个样本、Cool有4个样本,则

Split(TEMPERATURE) = - 4/14 * log2(4/14) - 6/14 * log2(6/14) - 4/14 * log2(4/14) = 1.5566567074628228

HUMIDITY属性

属性HUMIDITY有2个取值,其中Normal有7个样本、High有7个样本,则

Split(HUMIDITY) = - 7/14 * log2(7/14) - 7/14 * log2(7/14) = 1.0

WINDY属性

属性WINDY有2个取值,其中True有6个样本、False有8个样本,则

Split(WINDY) = - 6/14 * log2(6/14) - 8/14 * log2(8/14) = 0.9852281360342516

 

根据上面计算结果,我们可以计算信息增益率,如下所示:

(1)GR(OUTLOOK) = Info(OUTLOOK) / H(OUTLOOK) = 0.246/1.577406282852345 = 0.15595221261270145

(2)GR(TEMPERATURE) = Info(TEMPERATURE) / H(TEMPERATURE) = 0.029 / 1.5566567074628228 = 0.018629669509642094

(3)GR(HUMIDITY) = Info(HUMIDITY) / H(HUMIDITY) = 0.151/1.0 = 0.151

(4)GR(WINDY) = Info(WINDY) / H(WINDY) = 0.048/0.9852281360342516 = 0.048719680492692784

 

根据计算得到的信息增益率进行选择属性集中的属性(有上面的计算可知,应选OUTLOOK属性)作为决策树节点,对该节点进行分裂。

 

2.可以处理连续数值型属性

C4.5算法既可以处理离散型描述属性,也可以处理连续型描述属性。在选择某节点上的分支属性时,对于离散型描述属性,C4.5算法的处理方法与ID3相同,按照该属性本身的取值个数进行计算;对于某个连续型描述属性Ac,假设在某个节点上的数据集的样本数量为total,C4.5算法将作为以下处理:

  • 将该节点上的所有数据样本按照连续型描述的属性的具体数值,由小到大进行排序,得到属性值的取值序列{A1c,A2c,...,Atotalc}。
  • 在取值序列生成total-1个分割点。第i(0<i<total)个分割点的取值设置为Vi=(Aic+A(i+1)c)/2,它可以将该节点上的数据集划分为两个子集。
  • 从total-1个分割点中选择最佳分割点。对于每一个分割点划分数据集的方式,C4.5算法计算它的信息增益比,并且从中选择信息增益比最大的分割点来划分数据集。

3.采用了一种后后剪枝方法

避免树的高度无节制的增长,避免过度拟合数据,该方法使用训练样本集本身来估计剪枝前后的误差,从而决定是否真正剪枝。方法中使用的公式如下:

其中N是实例的数量,f=E/N为观察到的误差率(其中E为N个实例中分类错误的个数),q为真实的误差率,c为置信度(C4.5算法的一个输入参数,默认值为0.25),z为对应于置信度c的标准差,其值可根据c的设定值通过查正态分布表得到。通过该公式即可计算出真实误差率q的一个置信度上限,用此上限为该节点误差率e做一个悲观的估计:

通过判断剪枝前后e的大小,从而决定是否需要剪枝。

 

4.对于缺失值的处理

在某些情况下,可供使用的数据可能缺少某些属性的值。假如〈x,c(x)〉是样本集S中的一个训练实例,但是其属性A的值A(x)未知。处理缺少属性值的一种策略是赋给它结点n所对应的训练实例中该属性的最常见值;另外一种更复杂的策略是为A的每个可能值赋予一个概率。例如,给定一个布尔属性A,如果结点n包含6个已知A=1和4个A=0的实例,那么A(x)=1的概率是0.6,而A(x)=0的概率是0.4。于是,实例x的60%被分配到A=1的分支,40%被分配到另一个分支。这些片断样例(fractional examples)的目的是计算信息增益,另外,如果有第二个缺少值的属性必须被测试,这些样例可以在后继的树分支中被进一步细分。C4.5就是使用这种方法处理缺少的属性值。

 

二、部分代码示例

1、信息熵

1 double C4_5::entropy(int *attrClassCount, int classNum, int allNum){  2     double iEntropy = 0.0;  3     for(int i = 0; i < classNum; i++){  4         double temp = ((double)attrClassCount[i]) / allNum;  5         if(temp != 0.0)  6             iEntropy -= temp * (log(temp) / log(2.0));  7     }  8     return iEntropy;  9 }

 

2、信息增益率

1 double C4_5::gainRatio(int classNum, vector
attriCount, double pEntropy){ 2 int* attriNum = new int[attriCount.size()]; 3 int allNum = 0; 4 5 for(int i = 0; i < (int)attriCount.size(); i++){ 6 attriNum[i] = 0; 7 for(int j = 0; j < classNum; j++){ 8 attriNum[i] += attriCount[i][j]; 9 allNum += attriCount[i][j]; 10 } 11 } 12 double gain = 0.0; 13 double splitInfo = 0.0; 14 for(int i = 0; i < (int)attriCount.size(); i++){ 15 gain -= ((double)attriNum[i]) / allNum * entropy(attriCount[i], classNum, attriNum[i]); 16 splitInfo -= ((double)attriNum[i]) / allNum * (log(((double)attriNum[i])/allNum) / log(2.0)); 17 } 18 gain += pEntropy; 19 delete[] attriNum; 20 return (gain / splitInfo); 21 }

 

3、选取最大增益属性作为分类条件

1 int C4_5::chooseAttribute(vector
attrIndex, vector
* sampleCount){ 2 int bestIndex = 0; 3 double maxGainRatio = 0.0; 4 int classNum = (int)(decisions[attrIndex[(int)attrIndex.size()-1]]).size();//number of class 5 6 //computer the class entropy 7 int* temp = new int[classNum]; 8 int allNum = 0; 9 for(int i = 0; i < classNum; i++){ 10 temp[i] = sampleCount[(int)attrIndex.size()-1][i][i]; 11 allNum += temp[i]; 12 } 13 double pEntropy = entropy(temp, classNum, allNum); 14 delete[] temp; 15 16 //computer gain ratio for every attribute 17 for(int i = 0; i < (int)attrIndex.size()-1; i++){ 18 double gainR = gainRatio(classNum, sampleCount[i], pEntropy); 19 if(gainR > maxGainRatio){ 20 bestIndex = i; 21 maxGainRatio = gainR; 22 } 23 } 24 return bestIndex; 25 }

 

 

 

 

转载于:https://www.cnblogs.com/codingmengmeng/p/5419684.html

你可能感兴趣的文章
SQL语句优化
查看>>
校验银行卡号是否符合Luhn算法及生成符合Luhn算法的银行卡号
查看>>
MFC 双缓冲加载背景
查看>>
记录自己最近的学习状态
查看>>
hdu 1142 最短路+记忆化深搜---好题
查看>>
day 018 面向对象--约束和异常处理
查看>>
Day3_基本数据类型
查看>>
Fire Maze(广度优先搜索)
查看>>
Linux Kernel API
查看>>
oracle学习
查看>>
【C语言项目】贪吃蛇游戏(下)
查看>>
DevExpress第三方控件汉化的全部代码和使用方法
查看>>
二分查找算法(C#实现)
查看>>
vue项目中开启Eslint碰到的一些问题及其规范
查看>>
ES terms多值搜索及范围过滤深入剖析-搜索系统线上实战
查看>>
大咖专栏 | DevOps组织如何有效地实施MSA
查看>>
工厂模式
查看>>
忍不住了, 和大家聊聊怎么写简历吧, 关于简历的深度思考
查看>>
高并发编程
查看>>
(前端)html与css css 19、tab栏
查看>>