决策树的python实现方法


Posted in Python onNovember 18, 2014

本文实例讲述了决策树的python实现方法。分享给大家供大家参考。具体实现方法如下:

决策树算法优缺点:

优点:计算复杂度不高,输出结果易于理解,对中间值缺失不敏感,可以处理不相关的特征数据

缺点:可能会产生过度匹配的问题

适用数据类型:数值型和标称型

算法思想:

1.决策树构造的整体思想:

决策树说白了就好像是if-else结构一样,它的结果就是你要生成这个一个可以从根开始不断判断选择到叶子节点的树,但是呢这里的if-else必然不会是让我们认为去设置的,我们要做的是提供一种方法,计算机可以根据这种方法得到我们所需要的决策树。这个方法的重点就在于如何从这么多的特征中选择出有价值的,并且按照最好的顺序由根到叶选择。完成了这个我们也就可以递归构造一个决策树了

2.信息增益

划分数据集的最大原则是将无序的数据变得更加有序。既然这又牵涉到信息的有序无序问题,自然要想到想弄的信息熵了。这里我们计算用的也是信息熵(另一种方法是基尼不纯度)。公式如下:

数据需要满足的要求:

① 数据必须是由列表元素组成的列表,而且所有的列白哦元素都要具有相同的数据长度
② 数据的最后一列或者每个实例的最后一个元素应是当前实例的类别标签

函数:

calcShannonEnt(dataSet)
计算数据集的香农熵,分两步,第一步计算频率,第二部根据公式计算香农熵

splitDataSet(dataSet, aixs, value)
划分数据集,将满足X[aixs]==value的值都划分到一起,返回一个划分好的集合(不包括用来划分的aixs属性,因为不需要)

chooseBestFeature(dataSet)
选择最好的属性进行划分,思路很简单就是对每个属性都划分下,看哪个好。这里使用到了一个set来选取列表中唯一的元素,这是一中很快的方法

majorityCnt(classList)
因为我们递归构建决策树是根据属性的消耗进行计算的,所以可能会存在最后属性用完了,但是分类还是没有算完,这时候就会采用多数表决的方式计算节点分类

createTree(dataSet, labels)
基于递归构建决策树。这里的label更多是对于分类特征的名字,为了更好看和后面的理解。

#coding=utf-8

import operator

from math import log

import time
def createDataSet():

    dataSet=[[1,1,'yes'],

            [1,1,'yes'],

            [1,0,'no'],

            [0,1,'no'],

            [0,1,'no']]

    labels = ['no surfaceing','flippers']

    return dataSet, labels
#计算香农熵

def calcShannonEnt(dataSet):

    numEntries = len(dataSet)

    labelCounts = {}

    for feaVec in dataSet:

        currentLabel = feaVec[-1]

        if currentLabel not in labelCounts:

            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:

            reducedFeatVec = featVec[:axis]

            reducedFeatVec.extend(featVec[axis+1:])

            retDataSet.append(reducedFeatVec)

    return retDataSet

    

def chooseBestFeatureToSplit(dataSet):

    numFeatures = len(dataSet[0]) - 1#因为数据集的最后一项是标签

    baseEntropy = calcShannonEnt(dataSet)

    bestInfoGain = 0.0

    bestFeature = -1

    for i in range(numFeatures):

        featList = [example[i] for example in dataSet]

        uniqueVals = set(featList)

        newEntropy = 0.0

        for value in uniqueVals:

            subDataSet = splitDataSet(dataSet, i, value)

            prob = len(subDataSet) / float(len(dataSet))

            newEntropy += prob * calcShannonEnt(subDataSet)

        infoGain = baseEntropy -newEntropy

        if infoGain > bestInfoGain:

            bestInfoGain = infoGain

            bestFeature = i

    return bestFeature

            

#因为我们递归构建决策树是根据属性的消耗进行计算的,所以可能会存在最后属性用完了,但是分类

#还是没有算完,这时候就会采用多数表决的方式计算节点分类

def majorityCnt(classList):

    classCount = {}

    for vote in classList:

        if vote not in classCount.keys():

            classCount[vote] = 0

        classCount[vote] += 1

    return max(classCount)         

    

def createTree(dataSet, labels):

    classList = [example[-1] for example in dataSet]

    if classList.count(classList[0]) ==len(classList):#类别相同则停止划分

        return classList[0]

    if len(dataSet[0]) == 1:#所有特征已经用完

        return majorityCnt(classList)

    bestFeat = chooseBestFeatureToSplit(dataSet)

    bestFeatLabel = labels[bestFeat]

    myTree = {bestFeatLabel:{}}

    del(labels[bestFeat])

    featValues = [example[bestFeat] for example in dataSet]

    uniqueVals = set(featValues)

    for value in uniqueVals:

        subLabels = labels[:]#为了不改变原始列表的内容复制了一下

        myTree[bestFeatLabel][value] = createTree(splitDataSet(dataSet, 

                                        bestFeat, value),subLabels)

    return myTree

    

def main():

    data,label = createDataSet()

    t1 = time.clock()

    myTree = createTree(data,label)

    t2 = time.clock()

    print myTree

    print 'execute for ',t2-t1

if __name__=='__main__':

    main()

希望本文所述对大家的Python程序设计有所帮助。

Python 相关文章推荐
python2.7实现FTP文件下载功能
Apr 15 Python
python下解压缩zip文件并删除文件的实例
Apr 24 Python
Python3.5 Pandas模块之Series用法实例分析
Apr 23 Python
python3实现小球转动抽奖小游戏
Apr 15 Python
python读csv文件时指定行为表头或无表头的方法
Jun 26 Python
Python 实现交换矩阵的行示例
Jun 26 Python
Python中的self用法详解
Aug 06 Python
Python random模块制作简易的四位数验证码
Feb 01 Python
python爬虫开发之selenium模块详细使用方法与实例全解
Mar 09 Python
python实现将中文日期转换为数字日期
Jul 14 Python
Python中快速掌握Data Frame的常用操作
Mar 31 Python
什么是Python装饰器?如何定义和使用?
Apr 11 Python
linux 下实现python多版本安装实践
Nov 18 #Python
centos 下面安装python2.7 +pip +mysqld
Nov 18 #Python
朴素贝叶斯算法的python实现方法
Nov 18 #Python
使用django-suit为django 1.7 admin后台添加模板
Nov 18 #Python
DJANGO-ALLAUTH社交用户系统的安装配置
Nov 18 #Python
django 自定义用户user模型的三种方法
Nov 18 #Python
使用grappelli为django admin后台添加模板
Nov 18 #Python
You might like
php笔记之:AOP的应用
2013/04/24 PHP
FireFox浏览器使用Javascript上传大文件
2013/10/30 PHP
PHP基于CURL进行POST数据上传实例
2014/11/10 PHP
php获取指定范围内最接近数的方法
2015/06/02 PHP
JavaScript ( (__ = !$ + $)[+$] + ({} + $)[_/_] +({} + $)[_/_] )
2011/02/25 Javascript
基于jquery的DIV随滚动条滚动而滚动的代码
2012/07/20 Javascript
JS getAttribute和setAttribute(取得和设置属性)的使用介绍
2013/07/10 Javascript
node.js中的fs.exists方法使用说明
2014/12/17 Javascript
Javascript通过overflow控制列表闭合与展开的方法
2015/05/15 Javascript
深入学习JavaScript中的Rest参数和参数默认值
2015/07/28 Javascript
javascript读取文本节点方法小结
2016/12/15 Javascript
javascript显示系统当前时间代码
2016/12/29 Javascript
jquery Easyui Datagrid实现批量操作(编辑,删除,添加)
2017/02/20 Javascript
详解vue2路由vue-router配置(懒加载)
2017/04/08 Javascript
微信通过页面(H5)直接打开本地app的解决方法
2017/09/09 Javascript
vue.js默认路由不加载linkActiveClass问题的解决方法
2017/12/11 Javascript
Vue与Node.js通过socket.io通信的示例代码
2018/07/25 Javascript
jQuery md5加密插件jQuery.md5.js用法示例
2018/08/24 jQuery
微信小程序—setTimeOut定时器的问题及解决
2019/07/26 Javascript
js实现验证码干扰(静态)
2021/02/22 Javascript
pycharm在调试python时执行其他语句的方法
2018/11/29 Python
浅谈python的深浅拷贝以及fromkeys的用法
2019/03/08 Python
Windows下pycharm创建Django 项目(虚拟环境)过程解析
2019/09/16 Python
详解Python time库的使用
2019/10/10 Python
Python json读写方式和字典相互转化
2020/04/18 Python
django rest framework 自定义返回方式
2020/07/12 Python
Python常用数字处理基本操作汇总
2020/09/10 Python
python-jwt用户认证食用教学的实现方法
2021/01/19 Python
adidas官方旗舰店:德国运动用品制造商
2017/11/25 全球购物
波兰最早的运动鞋精品店之一:Street Supply
2019/08/29 全球购物
小学生美德少年事迹
2014/02/02 职场文书
高中生毕业评语
2014/12/30 职场文书
2015年档案管理工作总结
2015/04/08 职场文书
新娘父亲婚礼致辞
2015/07/27 职场文书
html+css实现滚动到元素位置显示加载动画效果
2021/08/02 HTML / CSS
MySQL自定义函数及触发器
2022/08/05 MySQL