Day 61-62 决策树(ID3)

news2024/11/26 22:20:59

代码:

package dl;

import java.io.FileReader;
import java.util.Arrays;
import weka.core.*;

/**
 * The ID3 decision tree inductive algorithm.
 */
public class ID3 {
    /**
     * The data.
     */
    Instances dataset;

    /**
     * Is this dataset pure (only one label)?
     */
    boolean pure;

    /**
     * The number of classes. For binary classification it is 2.
     */
    int numClasses;

    /**
     * Available instances. Other instances do not belong this branch.
     */
    int[] availableInstances;

    /**
     * Available attributes. Other attributes have been selected in the path
     * from the root.
     */
    int[] availableAttributes;

    /**
     * The selected attribute.
     */
    int splitAttribute;

    /**
     * The children nodes.
     */
    ID3[] children;

    /**
     * My label. Inner nodes also have a label. For example, <outlook = sunny,
     * humidity = high> never appear in the training data, but <humidity = high>
     * is valid in other cases.
     */
    int label;

    /**
     * The prediction, including queried and predicted labels.
     */
    int[] predicts;

    /**
     * Small block cannot be split further.
     */
    static int smallBlockThreshold = 3;

    /**
     ********************
     * The constructor.
     *
     * @param paraFilename
     *            The given file.
     ********************
     */
    public ID3(String paraFilename) {
        dataset = null;
        try {
            FileReader fileReader = new FileReader(paraFilename);
            dataset = new Instances(fileReader);
            fileReader.close();
        } catch (Exception ee) {
            System.out.println("Cannot read the file: " + paraFilename + "\r\n" + ee);
            System.exit(0);
        } // Of try

        dataset.setClassIndex(dataset.numAttributes() - 1);
        numClasses = dataset.classAttribute().numValues();

        availableInstances = new int[dataset.numInstances()];
        for (int i = 0; i < availableInstances.length; i++) {
            availableInstances[i] = i;
        } // Of for i
        availableAttributes = new int[dataset.numAttributes() - 1];
        for (int i = 0; i < availableAttributes.length; i++) {
            availableAttributes[i] = i;
        } // Of for i

        // Initialize.
        children = null;
        // Determine the label by simple voting.
        label = getMajorityClass(availableInstances);
        // Determine whether or not it is pure.
        pure = pureJudge(availableInstances);
    }// Of the first constructor

    /**
     ********************
     * The constructor.
     *
     * @param paraDataset
     *            The given dataset.
     ********************
     */
    public ID3(Instances paraDataset, int[] paraAvailableInstances, int[] paraAvailableAttributes) {
        // Copy its reference instead of clone the availableInstances.
        dataset = paraDataset;
        availableInstances = paraAvailableInstances;
        availableAttributes = paraAvailableAttributes;

        // Initialize.
        children = null;
        // Determine the label by simple voting.
        label = getMajorityClass(availableInstances);
        // Determine whether or not it is pure.
        pure = pureJudge(availableInstances);
    }// Of the second constructor

    /**
     **********************************
     * Is the given block pure?
     *
     * @param paraBlock
     *            The block.
     * @return True if pure.
     **********************************
     */
    public boolean pureJudge(int[] paraBlock) {
        pure = true;

        for (int i = 1; i < paraBlock.length; i++) {
            if (dataset.instance(paraBlock[i]).classValue() != dataset.instance(paraBlock[0])
                    .classValue()) {
                pure = false;
                break;
            } // Of if
        } // Of for i

        return pure;
    }// Of pureJudge

    /**
     **********************************
     * Compute the majority class of the given block for voting.
     *
     * @param paraBlock
     *            The block.
     * @return The majority class.
     **********************************
     */
    public int getMajorityClass(int[] paraBlock) {
        int[] tempClassCounts = new int[dataset.numClasses()];
        for (int i = 0; i < paraBlock.length; i++) {
            tempClassCounts[(int) dataset.instance(paraBlock[i]).classValue()]++;
        } // Of for i

        int resultMajorityClass = -1;
        int tempMaxCount = -1;
        for (int i = 0; i < tempClassCounts.length; i++) {
            if (tempMaxCount < tempClassCounts[i]) {
                resultMajorityClass = i;
                tempMaxCount = tempClassCounts[i];
            } // Of if
        } // Of for i

        return resultMajorityClass;
    }// Of getMajorityClass

    /**
     **********************************
     * Select the best attribute.
     *
     * @return The best attribute index.
     **********************************
     */
    public int selectBestAttribute() {
        splitAttribute = -1;
        double tempMinimalEntropy = 10000;
        double tempEntropy;
        for (int i = 0; i < availableAttributes.length; i++) {
            tempEntropy = conditionalEntropy(availableAttributes[i]);
            if (tempMinimalEntropy > tempEntropy) {
                tempMinimalEntropy = tempEntropy;
                splitAttribute = availableAttributes[i];
            } // Of if
        } // Of for i
        return splitAttribute;
    }// Of selectBestAttribute

    /**
     **********************************
     * Compute the conditional entropy of an attribute.
     *
     * @param paraAttribute
     *            The given attribute.
     *
     * @return The entropy.
     **********************************
     */
    public double conditionalEntropy(int paraAttribute) {
        // Step 1. Statistics.
        int tempNumClasses = dataset.numClasses();
        int tempNumValues = dataset.attribute(paraAttribute).numValues();
        int tempNumInstances = availableInstances.length;
        double[] tempValueCounts = new double[tempNumValues];
        double[][] tempCountMatrix = new double[tempNumValues][tempNumClasses];

        int tempClass, tempValue;
        for (int i = 0; i < tempNumInstances; i++) {
            tempClass = (int) dataset.instance(availableInstances[i]).classValue();
            tempValue = (int) dataset.instance(availableInstances[i]).value(paraAttribute);
            tempValueCounts[tempValue]++;
            tempCountMatrix[tempValue][tempClass]++;
        } // Of for i

        // Step 2.
        double resultEntropy = 0;
        double tempEntropy, tempFraction;
        for (int i = 0; i < tempNumValues; i++) {
            if (tempValueCounts[i] == 0) {
                continue;
            } // Of if
            tempEntropy = 0;
            for (int j = 0; j < tempNumClasses; j++) {
                tempFraction = tempCountMatrix[i][j] / tempValueCounts[i];
                if (tempFraction == 0) {
                    continue;
                } // Of if
                tempEntropy += -tempFraction * Math.log(tempFraction);
            } // Of for j
            resultEntropy += tempValueCounts[i] / tempNumInstances * tempEntropy;
        } // Of for i

        return resultEntropy;
    }// Of conditionalEntropy

    /**
     **********************************
     * Split the data according to the given attribute.
     *
     * @return The blocks.
     **********************************
     */
    public int[][] splitData(int paraAttribute) {
        int tempNumValues = dataset.attribute(paraAttribute).numValues();
        // System.out.println("Dataset " + dataset + "\r\n");
        // System.out.println("Attribute " + paraAttribute + " has " +
        // tempNumValues + " values.\r\n");
        int[][] resultBlocks = new int[tempNumValues][];
        int[] tempSizes = new int[tempNumValues];

        // First scan to count the size of each block.
        int tempValue;
        for (int i = 0; i < availableInstances.length; i++) {
            tempValue = (int) dataset.instance(availableInstances[i]).value(paraAttribute);
            tempSizes[tempValue]++;
        } // Of for i

        // Allocate space.
        for (int i = 0; i < tempNumValues; i++) {
            resultBlocks[i] = new int[tempSizes[i]];
        } // Of for i

        // Second scan to fill.
        Arrays.fill(tempSizes, 0);
        for (int i = 0; i < availableInstances.length; i++) {
            tempValue = (int) dataset.instance(availableInstances[i]).value(paraAttribute);
            // Copy data.
            resultBlocks[tempValue][tempSizes[tempValue]] = availableInstances[i];
            tempSizes[tempValue]++;
        } // Of for i

        return resultBlocks;
    }// Of splitData

    /**
     **********************************
     * Build the tree recursively.
     **********************************
     */
    public void buildTree() {
        if (pureJudge(availableInstances)) {
            return;
        } // Of if
        if (availableInstances.length <= smallBlockThreshold) {
            return;
        } // Of if

        selectBestAttribute();
        int[][] tempSubBlocks = splitData(splitAttribute);
        children = new ID3[tempSubBlocks.length];

        // Construct the remaining attribute set.
        int[] tempRemainingAttributes = new int[availableAttributes.length - 1];
        for (int i = 0; i < availableAttributes.length; i++) {
            if (availableAttributes[i] < splitAttribute) {
                tempRemainingAttributes[i] = availableAttributes[i];
            } else if (availableAttributes[i] > splitAttribute) {
                tempRemainingAttributes[i - 1] = availableAttributes[i];
            } // Of if
        } // Of for i

        // Construct children.
        for (int i = 0; i < children.length; i++) {
            if ((tempSubBlocks[i] == null) || (tempSubBlocks[i].length == 0)) {
                children[i] = null;
                continue;
            } else {
                // System.out.println("Building children #" + i + " with
                // instances " + Arrays.toString(tempSubBlocks[i]));
                children[i] = new ID3(dataset, tempSubBlocks[i], tempRemainingAttributes);

                // Important code: do this recursively
                children[i].buildTree();
            } // Of if
        } // Of for i
    }// Of buildTree

    /**
     **********************************
     * Classify an instance.
     *
     * @param paraInstance
     *            The given instance.
     * @return The prediction.
     **********************************
     */
    public int classify(Instance paraInstance) {
        if (children == null) {
            return label;
        } // Of if

        ID3 tempChild = children[(int) paraInstance.value(splitAttribute)];
        if (tempChild == null) {
            return label;
        } // Of if

        return tempChild.classify(paraInstance);
    }// Of classify

    /**
     **********************************
     * Test on a testing set.
     *
     * @param paraDataset
     *            The given testing data.
     * @return The accuracy.
     **********************************
     */
    public double test(Instances paraDataset) {
        double tempCorrect = 0;
        for (int i = 0; i < paraDataset.numInstances(); i++) {
            if (classify(paraDataset.instance(i)) == (int) paraDataset.instance(i).classValue()) {
                tempCorrect++;
            } // Of i
        } // Of for i

        return tempCorrect / paraDataset.numInstances();
    }// Of test

    /**
     **********************************
     * Test on the training set.
     *
     * @return The accuracy.
     **********************************
     */
    public double selfTest() {
        return test(dataset);
    }// Of selfTest

    /**
     *******************
     * Overrides the method claimed in Object.
     *
     * @return The tree structure.
     *******************
     */
    public String toString() {
        String resultString = "";
        String tempAttributeName = dataset.attribute(splitAttribute).name();
        if (children == null) {
            resultString += "class = " + label;
        } else {
            for (int i = 0; i < children.length; i++) {
                if (children[i] == null) {
                    resultString += tempAttributeName + " = "
                            + dataset.attribute(splitAttribute).value(i) + ":" + "class = " + label
                            + "\r\n";
                } else {
                    resultString += tempAttributeName + " = "
                            + dataset.attribute(splitAttribute).value(i) + ":" + children[i]
                            + "\r\n";
                } // Of if
            } // Of for i
        } // Of if

        return resultString;
    }// Of toString

    /**
     *************************
     * Test this class.
     *
     * @param args
     *            Not used now.
     *************************
     */
    public static void id3Test() {
        ID3 tempID3 = new ID3("C:\\Users\\86183\\IdeaProjects\\deepLearning\\src\\main\\java\\resources\\weather.arff");
        ID3.smallBlockThreshold = 3;
        tempID3.buildTree();

        System.out.println("The tree is: \r\n" + tempID3);

        double tempAccuracy = tempID3.selfTest();
        System.out.println("The accuracy is: " + tempAccuracy);
    }// Of id3Test

    /**
     *************************
     * Test this class.
     *
     * @param args
     *            Not used now.
     *************************
     */
    public static void main(String[] args) {
        id3Test();
    }// Of main
}// Of class ID3

结果:

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/770041.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Revit中如何创建水的效果及基坑?

一、Revit中如何创建水的效果? 我们在创建建筑的时候会遇上小池塘啊小池子之类的装饰景观&#xff0c;Revit又不像专业的3D软件那样可以有非常真实的水的效果&#xff0c;那么我们该如何简单创建水呢?下面来看步骤&#xff1a; 1、 在水池位置创建一块楼板&#xff0c;并将该…

C语言——文件操作(超全超详细)

C语言——文件操作 1. 什么是文件 磁盘上的文件是文件 但是在程序设计中&#xff0c;我们一般谈的文件有两种&#xff1a;程序文件、数据文件&#xff08;从文件功能的角度来分类的&#xff09; 1.1 程序文件 包括源程序文件&#xff08;后缀为.c&#xff09;&#xff0c;目…

椒图--分析中心

护网的时候我们要把右边的开关开启。开启就会对系统全量的记录&#xff0c;包含有网络行为日志&#xff0c;就会检测我们服务器里面的链接&#xff0c;端口箭头&#xff0c;内内网暴露的链接&#xff1b;进程操作日志&#xff0c;就可以看我们系统创建了哪些进程&#xff0c;就…

【操作系统】Liunx项目自动化构建工具-make/Makefile

Yan-英杰的主页 悟已往之不谏 知来者之可追 C程序员&#xff0c;2024届电子信息研究生 目录 一、背景 二、Makefile 实现 Makefile依赖 依赖关系 makefile的工作原理 项目清理 补充&#xff1a; .PHONY是什么&#xff1f; Linux如何进行多行注释&#xff1a; 说明&#xf…

app 元素定位失败了,怎么办?一看我的做法,惊呆了!

粉丝们在日常的android app自动化测试工作当中&#xff0c;元素定位时会遇到以下类似的报错&#xff1a; 然后来问博主&#xff0c;这是啥情况&#xff1f; 我一般都会送上亲切的关怀&#xff1a; 1&#xff09;adb能识别到设备吗&#xff1f; 2&#xff09;设备有被其它的程…

VUE+element Input框 实现输入内容可自适应文本高度,换行(空格换行,enter发送)阻止文本域的回车事件

需求 输入框实现输入内容自适应高度 以及可以换行 使用官方文档提供的属性 代码 <el-input clearable autosize type"textarea" :placeholder"$t(navbar.pleaseInput)"v-model"inputText" change"inputChange" keyup.enter.na…

数据分析之Matplotlib

文章目录 1. 认识数据可视化和Matplotlib安装2. 类型目录3. 图标名称title4. 处理图形中的中文问题5. 设置坐标轴名称&#xff0c;字体大小&#xff0c;线条粗细6. 绘制多个线条和zorder叠加顺序7. 设置x轴刻度xticks和y轴刻度yticks8. 显示图表show9. 设置图例legend10. 显示线…

Ceph简介及部署

Ceph Ceph一、存储基础1、单机存储设备2、Ceph 简介3、Ceph 优势5、Ceph 架构6、Ceph 核心组件7、OSD 存储后端8、Ceph 数据的存储过程9、Ceph 版本发行生命周期10、Ceph 集群部署 二、部署ceph-deploy Ceph 集群前环境配置1、关闭 selinux 与防火墙2、根据规划设置主机名3、配…

全网火爆,pytest自动化测试框架从0-1精通实战,你的进阶之路...

目录&#xff1a;导读 前言一、Python编程入门到精通二、接口自动化项目实战三、Web自动化项目实战四、App自动化项目实战五、一线大厂简历六、测试开发DevOps体系七、常用自动化测试工具八、JMeter性能测试九、总结&#xff08;尾部小惊喜&#xff09; 前言 1、运行方式 命令…

(68Ga)Nota-prgd2,1345968-02-6,通过镓标记的NOTA衍生物

文章编辑来自于&#xff1a;陕西新研博美生物科技有限公司MISS.wu​ (68Ga)Nota-prgd2| CAS&#xff1a;1345968-02-6| 纯度&#xff1a;95% PART1-----(68Ga)Nota-prgd2结构式 PART2-----试剂参数信息 CAS&#xff1a;1345968-02-6 外观&#xff08;Appearance&#xff09;…

网络安全(黑客)学习笔记

0基础学网安或者提升巩固网安技术的小伙伴有福了&#xff01; 本篇整合了网络安全全知识点&#xff0c;零基础也适用&#xff01; 本篇涵盖内容及其全面&#xff0c;强烈推荐收藏&#xff01; 一、学习网络安全会遇到什么问题呢&#xff1f; 1、学习基础内容多时间长 2、难…

周报(1)

文章预览&#xff1a; 本周内容&#xff1a;Python语言的学习和pytorch安装配置1 Python基础知识1.1 交互式解释器1.2 数和表达式1.3 变量1.4 获取用户输入1.5 函数1.6 模块1.7 字符串1.7.1 单引号字符串以及对引号转义1.7.2 拼接字符串1.7.3 字符串表示str 和repr Pytorch 的安…

vue 限制表情输入

在main.js中加入下列代码 import emoji from ./util/emojiVue.directive(emoji,emoji) 在util文件夹中加入emoji.js 下列代码 const findEle (parent, type) > { return parent.tagName.toLowerCase() type ? parent : parent.querySelector(type)}const emoji {bi…

vite vue3进行多环境打包配置

需求&#xff1a; 对此vite创建的vu3项目进行构建&#xff0c;项目分为四个环境&#xff1a;本地、测试、预发、生产 1.在项目根目录创建四个文件夹 .env.development .env.test .env.pre .env.production 2.配置不同环境的 地址和打包文件名 具体例子如下&#xff1a; …

手机验证码登录 -- 手把手教你做ssm+springboot入门后端项目黑马程序员瑞吉外卖(七)

文章目录 前言一、短信发送1. 短信服务介绍2. 阿里云短信服务3. 代码开发 二、手机验证码登录1. 需求分析2. 数据模型3. 代码开发4. 功能测试 总结 前言 为了巩固所学的知识&#xff0c;作者尝试着开始发布一些学习笔记类的博客&#xff0c;方便日后回顾。当然&#xff0c;如果…

项目名称:网络聊天室

目录 一&#xff0c;简述 二&#xff0c;项目要求 三&#xff0c;程序流程图 服务器端&#xff1a; 客户端&#xff1a; 四&#xff0c;相关知识点 通信流程&#xff1a; 函数接口&#xff1a; 五&#xff0c;代码实现 客户端&#xff1a; 服务器&#xff1a; 主程序…

Android性能优化——启动优化

App 的启动速度是用户的第一体验&#xff0c;互联网中有一个八秒定律&#xff0c;如果用户等待八秒App 还没打开&#xff0c;70%的用户都会停止等待 一、启动分类 官方 App startup time 冷启动 耗时最多&#xff0c;衡量标准 热启动 最快。 后台&#xff5e;前台 温启动…

Git 新建本地仓库,推送到远程仓库

1、在项目的根目录右键 Git Bash Here 打开目录下的 git 命令 2、输入 git init 回车&#xff0c;初始化项目&#xff0c;把这个项目变成一个Git可以管理的仓库 项目根目录出现 .git 隐藏文件夹。这个目录是Git来跟踪管理版本库的&#xff0c;没事千万不要手动修改这个目录里面…

MateBook E Go Wi-Fi性能版(GK-W76)工厂模式win11原厂系统,含F10智能恢复功能

HUAWEI华为MateBook E平板笔记本电脑(GK-W76)原装出厂Windows11系统包&#xff0c;带F10一键智能还原 系统自带所有驱动、出厂主题壁纸LOGO、Office办公软件、华为电脑管家等预装程序 所需要工具&#xff1a;16G或以上的U盘 文件格式&#xff1a;zip 文件大小&#xff1a;1…

Linux基础(三)端口、进程及主机状态管理、环境变量、文件管理

目录 端口 nmap netstat 进程管理 查看进程 关闭进程 主机状态监控 系统资源top命令 磁盘信息监控 网络状态监控 环境变量 $符号 自己设置环境变量 自定义环境变量PATH Linux的文件和下载 压缩和解压 tar命令 zip和unzip命令 端口 每个电脑有一个ip地址&#xff…