机器学习:贝叶斯分类器(二)——高斯朴素贝叶斯分类器代码实现

一 高斯朴素贝叶斯分类器代码实现

  • 网上搜索不调用sklearn实现的朴素贝叶斯分类器基本很少,即使有也是结合文本分类的多项式或伯努利类型,因此自己写了一遍能直接封装的高斯类型NB分类器,当然与真正的源码相比少了很多属性和方法,有兴趣的可以自己添加。代码如下(有详细注释):
class NaiveBayes():
    ‘‘‘高斯朴素贝叶斯分类器‘‘‘

    def __init__(self):

        self._X_train = None
        self._y_train = None
        self._classes = None
        self._priorlist = None
        self._meanmat = None
        self._varmat = None

    def fit(self, X_train, y_train):

        self._X_train = X_train
        self._y_train = y_train
        self._classes = np.unique(self._y_train)                       #  得到各个类别
        priorlist = []
        meanmat0 = np.array([[0, 0, 0, 0]])
        varmat0 = np.array([[0, 0, 0, 0]])
        for i, c in enumerate(self._classes):
            # 计算每个种类的平均值,方差,先验概率
            X_Index_c = self._X_train[np.where(self._y_train == c)]        # 属于某个类别的样本组成的“矩阵”
            priorlist.append(X_Index_c.shape[0] / self._X_train.shape[0])  # 计算类别的先验概率
            X_index_c_mean = np.mean(X_Index_c, axis=0, keepdims=True)     # 计算该类别下每个特征的均值,结果保持二维状态[[3 4 6 2 1]]
            X_index_c_var = np.var(X_Index_c, axis=0, keepdims=True)       # 方差
            meanmat0 = np.append(meanmat0, X_index_c_mean, axis=0)         # 各个类别下的特征均值矩阵罗成新的矩阵,每行代表一个类别。
            varmat0 = np.append(varmat0, X_index_c_var, axis=0)
        self._priorlist = priorlist
        self._meanmat = meanmat0[1:, :]                                    #除去开始多余的第一行
        self._varmat = varmat0[1:, :]

    def predict(self,X_test):

        eps = 1e-10                                                        # 防止分母为0
        classof_X_test = []                                                #用于存放测试集中各个实例的所属类别
        for x_sample in X_test:
            matx_sample = np.tile(x_sample,(len(self._classes),1))         #将每个实例沿列拉长,行数为样本的类别数
            mat_numerator = np.exp(-(matx_sample - self._meanmat) ** 2 / (2 * self._varmat + eps))
            mat_denominator = np.sqrt(2 * np.pi * self._varmat + eps)
            list_log = np.sum(np.log(mat_numerator/mat_denominator),axis=1)# 每个类别下的类条件概率相乘后取对数
            prior_class_x = list_log + np.log(self._priorlist)             # 加上类先验概率的对数
            prior_class_x_index = np.argmax(prior_class_x)                 # 取对数概率最大的索引
            classof_x = self._classes[prior_class_x_index]                 # 返回一个实例对应的类别
            classof_X_test.append(classof_x)
        return classof_X_test

    def score(self, X_test, y_test):

        j = 0
        for i in range(len(self.predict(X_test))):
            if self.predict(X_test)[i] == y_test[i]:
                j += 1
        return (‘accuracy: {:.10%}‘.format(j / len(y_test)))
  • 对于手动实现的高斯型NB分类器,利用鸢尾花数据进行测试,与调用sklearn库的分类器结果差不多,基本在93-96徘徊。这是由于多次进行二八切分,相当于多次留出法。为计算更准确精度,可进行交叉验证并选择多个评价方法,这里不再实现。
import numpy as np
from sklearn import datasets
from sklearn.model_selection import train_test_split
from sklearn import preprocessing
# 获取数据集,并进行8:2切分
iris = datasets.load_iris()
X = iris.data
y = iris.target
# print(X)
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2)

nb = NaiveBayes()
nb.fit(X_train,y_train)
print(nb.predict(X_test))
print(nb.score(X_test,y_test))
#输出结果如下:
[0, 2, 1, 1, 1, 2, 1, 0, 2, 0, 1, 1, 1, 0, 2, 2, 2, 2, 0, 1, 1, 0, 2, 2, 2, 0, 1, 0, 1, 0]
accuracy: 96.6666666667%

二 其他

  • 基于属性条件独立性假设的朴素贝叶斯,在现实中往往很难成立,因此产生了“半朴素贝叶斯分类器”。其基本思想是适当考虑一部分属性间的相互依赖信息,从而既不需要进行完全联合概率计算,又不至于彻底忽略比较强的属性依赖关系。“独依赖估计”是最常用的一种策略,即假设每个属性在类别之外最多依赖一个其他属性。包括SPODE方法,TAN方法,AODE方法等。
  • np.unique():返回原来array中不重复元素组成的新array,元素从小到大。
y = np.array([1, 2, 9, 1,2,3])
classes = np.unique(y)                     # 返回y中所有不重复的元素组成的新array([1,2,3,9])
print(classes)                             # 结果为np.array([1,2,3,9])
  • np.where():对array进行操作
‘‘‘
1. np.where(condition, x, y)
满足条件(condition),满足进行x操作,不满足进行y操作
‘‘‘
a= np.array([[9, 7, 3], [4, 5, 2], [6, 3, 8]])
b=np.where(a > 5, 1, 0)               #对于a中的元素如果大于5,则改写成1,否则写成0.
print(b)
输出结果:
[[1 1 0]
 [0 0 0]
 [1 0 1]]
‘‘‘
2. np.where(condition)
只有条件 (condition),没有x和y,则输出满足条件元素的坐标 (等价于numpy.nonzero)。
这里的坐标以tuple的形式给出,通常原数组有多少维,输出的tuple中就包含几个数组,分别对应符合条件元素的各维坐标。
‘‘‘
c = np.array([[9, 7, 3], [4, 5, 2], [6, 3, 8]])
d = np.where(c > 5)                                                #条件为元素大于5
print(d)
输出结果如下(元组):
(array([0, 0, 2, 2], dtype=int64), array([0, 1, 0, 2], dtype=int64)) 表示下表为 00,01 20,22的元素满足条件。

a = np.array([1,3,6,9,0])
b = np.where(a > 5)
print(b)
输出结果(array([2, 3], dtype=int64),)表示坐标为2和3的元素满足,注意末尾的逗号,表明一维时实质输出元组为二维,2_,3_只不过后面没有而已,a维数大于等于2时,元组和a维数相同。
输出的结果是可以直接作为数组下标。
x = np.array([[1, 5, 8, 1], [2, 4, 6, 8], [3, 6, 7, 9], [6, 8, 3, 1]])
print(x[b])  结果为x的第2,3行组成的数组[[3  6 7 9]  [6  8 3 1]],等价于x[[2,3]],x[2,3]为输出为元素9,x[[2],[3]]输出数组[9]。

原文地址:https://www.cnblogs.com/lyxML/p/9526089.html

时间: 2024-08-08 18:47:13

机器学习:贝叶斯分类器(二)——高斯朴素贝叶斯分类器代码实现的相关文章

机器学习之路: python 朴素贝叶斯分类器 预测新闻类别

使用python3 学习朴素贝叶斯分类api 设计到字符串提取特征向量 欢迎来到我的git下载源代码: https://github.com/linyi0604/kaggle 1 from sklearn.datasets import fetch_20newsgroups 2 from sklearn.cross_validation import train_test_split 3 # 导入文本特征向量转化模块 4 from sklearn.feature_extraction.text

从朴素贝叶斯分类器到贝叶斯网络(上)

一.贝叶斯公式(一些必备的数学基础) 贝叶斯(Thomas Bayes)是生活在十八世纪的一名英国牧师和数学家.因为历史久远,加之他没有太多的著述留存,今天的人们对贝叶斯的研究所知甚少.唯一知道的是,他提出了概率论中的贝叶斯公式.但从他曾经当选英国皇家科学学会会员(类似于院士)来看,他的研究工作在当时的英国学术界已然受到了普遍的认可. 事实上,在很长一段时间里,人们都没有注意到贝叶斯公式所潜藏的巨大价值.直到二十世纪人工智能.机器学习等崭新学术领域的出现,人们才从一堆早已蒙灰的数学公式中发现了贝

朴素贝叶斯分类器的应用 Naive Bayes classifier

一.病人分类的例子 让我从一个例子开始讲起,你会看到贝叶斯分类器很好懂,一点都不难. 某个医院早上收了六个门诊病人,如下表. 症状 职业 疾病 打喷嚏 护士 感冒  打喷嚏 农夫 过敏  头痛 建筑工人 脑震荡  头痛 建筑工人 感冒  打喷嚏 教师 感冒  头痛 教师 脑震荡 现在又来了第七个病人,是一个打喷嚏的建筑工人.请问他患上感冒的概率有多大? 根据贝叶斯定理: P(A|B) = P(B|A) P(A) / P(B) 可得 P(感冒|打喷嚏x建筑工人)  = P(打喷嚏x建筑工人|感冒)

朴素贝叶斯分类器的应用-转载加我的理解注释

生活中很多场合需要用到分类,比如新闻分类.病人分类等等. 本文介绍朴素贝叶斯分类器(Naive Bayes classifier),它是一种简单有效的常用分类算法. 一.病人分类的例子 让我从一个例子开始讲起,你会看到贝叶斯分类器很好懂,一点都不难. 某个医院早上收了六个门诊病人,如下表. 症状 职业 疾病 打喷嚏 护士 感冒  打喷嚏 农夫 过敏  头痛 建筑工人 脑震荡  头痛 建筑工人 感冒  打喷嚏 教师 感冒  头痛 教师 脑震荡 现在又来了第七个病人,是一个打喷嚏的建筑工人.请问他患

PGM学习之三 朴素贝叶斯分类器(Naive Bayes Classifier)

介绍朴素贝叶斯分类器的文章已经很多了.本文的目的是通过基本概念和微小实例的复述,巩固对于朴素贝叶斯分类器的理解. 一 朴素贝叶斯分类器基础回顾 朴素贝叶斯分类器基于贝叶斯定义,特别适用于输入数据维数较高的情况.虽然朴素贝叶斯分类器很简单,但是它确经常比一些复杂的方法表现还好. 为了简单阐述贝叶斯分类的基本原理,我们使用上图所示的例子来说明.作为先验,我们知道一个球要么是红球要么是绿球.我们的任务是当有新的输入(New Cases)时,我们给出新输入的物体的类别(红或者绿).这是贝叶斯分类器的典型

机器学习经典算法详解及Python实现---朴素贝叶斯分类及其在文本分类、垃圾邮件检测中的应用

摘要: 朴素贝叶斯分类是贝叶斯分类器的一种,贝叶斯分类算法是统计学的一种分类方法,利用概率统计知识进行分类,其分类原理就是利用贝叶斯公式根据某对象的先验概率计算出其后验概率(即该对象属于某一类的概率),然后选择具有最大后验概率的类作为该对象所属的类.总的来说:当样本特征个数较多或者特征之间相关性较大时,朴素贝叶斯分类效率比不上决策树模型:当各特征相关性较小时,朴素贝叶斯分类性能最为良好.另外朴素贝叶斯的计算过程类条件概率等计算彼此是独立的,因此特别适于分布式计算.本文详述了朴素贝叶斯分类的统计学

朴素贝叶斯分类算法介绍及python代码实现案例

朴素贝叶斯分类算法 1.朴素贝叶斯分类算法原理 1.1.概述 贝叶斯分类算法是一大类分类算法的总称 贝叶斯分类算法以样本可能属于某类的概率来作为分类依据 朴素贝叶斯分类算法是贝叶斯分类算法中最简单的一种 注:朴素的意思是条件概率独立性 P(A|x1x2x3x4)=p(A|x1)*p(A|x2)p(A|x3)p(A|x4)则为条件概率独立 P(xy|z)=p(xyz)/p(z)=p(xz)/p(z)*p(yz)/p(z) 1.2.算法思想 朴素贝叶斯的思想是这样的: 如果一个事物在一些属性条件发生

朴素贝叶斯分类算法原理分析与代码实现

前言 本文介绍机器学习分类算法中的朴素贝叶斯分类算法并给出伪代码,Python代码实现. 词向量 朴素贝叶斯分类算法常常用于文档的分类,而且实践证明效果是挺不错的. 在说明原理之前,先介绍一个叫词向量的概念. --- 它一般是一个布尔类型的集合,该集合中每个元素都表示其对应的单词是否在文档中出现. 对应关系和词汇表一一对应. 比如说,词汇表只有三个单词:'apple', 'orange', 'melo',某文档中,apple和melo出现过,那么其对应的词向量就是 {1, 0, 1}. 这种模型

第五篇:朴素贝叶斯分类算法原理分析与代码实现

前言 本文介绍机器学习分类算法中的朴素贝叶斯分类算法并给出伪代码,Python代码实现. 词向量 朴素贝叶斯分类算法常常用于文档的分类,而且实践证明效果挺不错的. 在说明原理之前,先介绍一个叫词向量的概念. --- 它一般是一个布尔类型的集合,该集合中每个元素都表示其对应的单词是否在文档中出现. 比如说,词汇表只有三个单词:'apple', 'orange', 'melo',某文档中,apple和melo出现过,那么其对应的词向量就是 {1, 0, 1}. 这种模型通常称为词集模型,如果词向量元