本文主要详细介绍了Python机器学习的决策树算法,具有一定的参考价值。感兴趣的朋友可以参考一下。
一、决策树原理
决策树是以样本的属性为节点,属性值为分支的树形结构。
决策树的根节点是所有样本中信息量最大的属性。树的中间节点是以该节点为根的子树中包含的样本子集中信息量最大的属性。决策树的叶节点是样本的类别值。决策树是一种知识表示形式,是对所有样本数据的高度概括。决策树能准确识别所有样本的类别,并能有效识别新样本的类别。
决策树ID3的基本思想;
首先找出最有判别力的属性,将样本分成若干子集,每个子集选择最有判别力的属性进行划分,直到所有子集只包含同一类型的数据。获取最后一棵决策树。
J.R.Quinlan的工作主要是介绍信息论中的信息增益,他称之为信息增益。作为属性辨别能力的一种度量,他设计了一种构造决策树的递归算法。
例子很容易理解:
对于气候分类问题,属性是:
天气(A1)值为:晴天、多云和雨天。
空气温度(A2)为冷、中和热。
湿度(A3)高且正常。
风(A4)的值是:有风和无风。
每个样本属于不同的类别。这个例子只有两类,分别是P类和N类,P类和N类的例子分别叫做正例和反例。把一些已知的正面例子和反面例子放在一起,得到训练集。
ID3算法得到一个正确分类训练集中每个样本的决策树,如下图所示。
决策树是类别名,即P或n,其他节点由样本的属性组成,每个属性的不同值对应一个分支。
要对样本进行分类,从树根开始测试,根据属性值向下分支到较低的节点,然后测试节点。该过程一直进行到叶子节点,并且判断样本属于叶子节点所标记的类别。
用图来判断一个具体的例子,
一天早上,气候被描述为:
天气:多云
温度:冷
湿度:正常
风:没有风。
属于哪种气候?-从图中可以判断出样本被归类为p类。
ID3是从表的训练集构建一个类似决策树的图。实际上,可以正确分类训练集的决策树不止一个。昆兰的ID3算法可以得到节点最少的决策树。
Id算法:
1.对于当前的例子集,计算每个属性的信息增益;
2.选择信息增益最大的属性AK;
3.将Ak处取值相同的例子归入同一个子集,如果Ak取几个值,就会得到几个子集;
4.递归调用包含正例与反例的子集的树构建算法;
5.如果子集只包含正例或反例,用P或N标记对应的分支,返回调用处。
每当涉及到树时,经常使用递归。
气候分类的具体计算包括:
1.信息熵的计算:其中s是样本的集合,P(ui)是类别I的出现概率:
|S|表示示例集S的总数,而|ui|表示类别ui的示例数。九个正面例子和五个负面例子是:
P(u1)=9/14
P(u2)=5/14
h(S)=(9/14)log(14/9)(5/14)log(14/5)=0.94位
2.信息增益的计算:
其中A是属性,Value(A)是属性A的值的集合,V是A的某个属性值,Sv是S中A的值为V的样本的集合,| Sv |是Sv中包含的样本数。
以属性A1为例,根据信息增益的计算公式,属性A1的信息增益为
S=[9,5-] //原始样本集中有14个样本,9个正例,5个反例。
S=[2,3-]//属性A1有5个例子,值为sunny,2个正,3个负。
多云s=[4,0-] //属性A1有4个多云样本,其中4个为正值,0个为负值。
Rain=[3,2-] //属性A1值明确的例子有5个,3个正,2个负。
因此
3.结果是
属性A1具有最大的信息增益,因此选择它作为根节点。
4.构建t
其中S2中的例子全属于P类,因此对应分枝标记为p,其余两个子集既含有正例又含有反例,将递归调用建树算法。
5、递归建树
分别对S1和S3子集递归调用ID3算法,在每个子集中对各属性求信息增益。
(1)对S1,湿度属性信息增益最大,以它为该分枝的根结点,再向下分枝。湿度取高的例子全为普通类,该分枝标记不知道。取值正常的例子全为P类,该分枝标记p。
(2)对S3,风属性信息增益最大,则以它为该分枝根结点。再向下分枝,风取有风时全为普通类,该分枝标记不知道。取无风时全为P类,该分枝标记p。
二、PYTHON实现决策树算法分类
本代码为机器学习在行动第三章例子,亲测无误。
1、计算给定数据尚农数据的函数:
def calcShannonEnt(数据集):
#计算香农值
numEntries=len(数据集)
labelCounts={}
对于数据集中的featVec为所有数据创建字典
currentLabel=featVec[-1]
如果当前标签不在labelCounts.keys()中:
标签数量[当前标签]=0
标签数量[当前标签]=1
shannonEnt=0.0
对于标签帐户中的密钥:
prob=float(标签计数[键])/numEntries
shannonEnt -=prob*log(prob,2)#获取日志值
返回shannonEnt
2.创建数据的函数
def createDataSet():
数据集=[[1,1,'是'],
[1,1,'是'],
[1,0,'否'],
[0,1,'否'],
[0,1,'否']]
标签=['禁止浮出水面','脚蹼]
返回数据集,标签
3.划分数据集,按照给定的特征划分数据集
定义splitDataSet(数据集,轴,值):
retDataSet=[]
对于数据集中的featVec:
if featVec[轴]==值:#抽象未来
reducedFeatVec=featVec[:axis]
reducedfeatvec。扩展(featVec[轴1:])
ret数据集。append(reducedFeatVec)
返回retDataSet
4.选择最好的数据集划分方式
def chooseBestFeatureToSplit(数据集):
numFeatures=len(dataSet[0])-1
baseEntropy=calcShannonEnt(数据集)
bestInfoGain=0.0bestFeature=-1
对于范围内的I(数字特征):
feat list=[示例[i]数据集中的示例]
uniqueVals=set(featList)
新熵=0.0
对于唯一值:
subDataSet=splitDataSet(数据集,我,值)
prob=len(子数据集)/float(len(数据集))
newEntropy=prob * calcShannonEnt(子数据集)
信息增益=基础熵-新熵
if(infoGain bestInfoGain):
bestInfoGain=信息增益
bestFeature=i
返回最佳功能
5.递归创建树
用于找出出现次数最多的分类名称的函数
大多数人(类别列表):
classCount={}
对于类别列表中的投票:
如果投票不在classCount.keys()中:classCount[vote]=0
classCount[vote]=1
sortedClassCount=sorted(类计数。ITER项(),key=operator.itemgetter(1),reverse=True)
返回sortedClassCount[0][0]
用于创建树的函数代码
定义创建树(数据集,标签):
class list=[示例[-1]例如在数据集中]
#类型相同,因此停止分类
如果类列表。count(类列表[0])==len(类列表):
返回类列表[0]
#遍历所有特征并选择最常见的特征
if (len(dataSet[0])==1):
返回majorityCnt(类别列表)
最佳壮举=chooseBestFeatureToSplit(数据集)
bestFeatLabel=labels[bestFeat]
myTree={bestFeatLabel:{}}
德尔(标签[最佳成绩])
#获取获得全部属性的列表
featValues=[example[bestFeat]数据集中的示例]
唯一值=集合(特征值)
对于唯一值:
子标签=标签[:]
myTree[bestFeatLabel][value]=创建树(拆分数据集(dataSet,bestFeat,value),子标签)
返回我的树
然后是在大蟒名利提示符号输入如下命令:
myDat,labels=trees.createDataSet()
myTree=trees.createTree(myDat,labels)
打印我的树
结果是:
{ '不显示':{0:'否,1: {'flippers': {0:'否',1:'是' }}}
6.实用决策树进行分类的函数
定义分类(输入树,特征标签,测试向量):
firstStr=inputTree.keys()[0]
secondDict=inputTree[firstStr]
专长索引=专长标签。索引(第一个字符串)
对于secondDict.keys()中的关键:
if testVec[featIndex]==key:
如果类型(secondDict[key]).__name__=='dict ':
class label=classify(第二个字典[key],featLabels,testVec)
else:class label=second dict[key]
返回类别标签
在计算机编程语言命令提示符,输入:
trees.classify(我的树,标签,[1,0])
得到结果:
没有
恭喜你。哦是的。你做到了。
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持我们。
郑重声明:本文由网友发布,不代表盛行IT的观点,版权归原作者所有,仅为传播更多信息之目的,如有侵权请联系,我们将第一时间修改或删除,多谢。