详尽分享贝叶斯算法的基本原理和算法实现

简介: 详尽分享贝叶斯算法的基本原理和算法实现

一. 贝叶斯公式推导

  朴素贝叶斯分类是一种十分简单的分类算法,叫它朴素是因为其思想基础的简单性:就文本分类而言,它认为词袋中的两两词之间的关系是相互独立的,即一个对象 的特征向量中每个维度都是相互独立的。例如,黄色是苹果和梨共有的属性,但苹果 和梨是相互独立的。这是朴素贝叶斯理论的思想基础。现在我们将它扩展到多维的情况:

  朴素贝叶斯分类的正式定义如下:

  1.设 x={a1,a2,…,am}//代码效果参考:为一个待分类项,而每个 a 为 x 的一个特征属性。

  2.有类别集合 C={y1,y2,…,yn}。

  3.计算 P( y1|x) ,P( y2|x),…, P( yn|x)。

  4.如果 P( yk|x) =max{P( y1|x),P( y2|x),…, P( yn|x)},则 x∈yk。

  那么现在的关键就是如何计算第 3 步中的各个条件概率。我们可以这么做:

    (1) 找到一个已知分类的待分类项集合,也就是训练集。

    (2) 统计得到在各类别下各个特征属性的条件概率估计。即:

         P(a1|y1) , P(a2|y1),…, P(am|y1);

        P(a1|y2) , P(a2|y2),…, P(am|y2);

        P(am|yn) , P(am|yn),…, P(am|yn)。

    (3) 如果各个特征属性是条件独立的(或者我们假设它们之间是相互独立的),则根 据贝叶斯定理有如下推导:

      因为分母对于所有类别为常数,只要将分子最大化皆可。又因为各特征属性是条 件独立的,所以有:

  根据上述分析,朴素贝叶斯分类的流程可以表示如下: 第一阶段:训练数据生成训练样本集:TF-IDF

  第二阶段:对每个类别计算 P(yi)

  第三阶段:对每个特征属性计算所有划分的条件概率 第四阶段:对每个类别计算 P( x | yi ) P( yi )

  第五阶段:以 P( x | yi ) P( yi ) 的最大项作为 x 的所属类别

  二. 朴素贝叶斯算法实现

  使用简单的英文语料作为数据集:

def loadDataSet():

  postingList=【【'my', 'dog', 'has', 'flea', 'problems', 'help', 'please'】,

  【'maybe', 'not', 'take', 'him', 'to', 'dog', 'park', 'stupid'】,

  【'my', 'dalmation', 'is', 'so', 'cute', 'I', 'love', 'him','my'】, 【'stop', 'posting', 'stupid', 'worthless', 'garbage'】,

  【'mr', 'licks', 'ate', 'my', 'steak', 'how', 'to', 'stop', 'him'】,

  【'quit', 'buying', 'worthless', 'dog', 'food', 'stupid'】】 classVec = 【0,1,0,1,0,1】 #1 is abusive, 0 not

  return postingList,classVec

  postList 是训练集文本,classVec 是每个文本对应的分类。

  根据上节的步骤,逐步实现贝叶斯算法的全过程:

  1.编写一个贝叶斯算法类,并创建默认的构造方法:

class NBayes(object): def __init__(self):

self.vocabulary= 【】 # 词典

self.idf=0 # 词典的 idf 权值向量

self.tf=0 # 训练集的权值矩阵

self.tdm=0 # P(x|yi)

self.Pcates = {} # P(yi)--是个类别字典

self.labels=【】 # 对应每个文本的分类,是个外部导入的列表

self.doclength = 0 # 训练集文本数

self.vocablen = 0 # 词典词长

self.testset = 0 # 测试集

  2.导入和训练数据集,生成算法必须的参数和数据结构:

def train_set(self,trainset,classVec):

self.cate_prob(classVec) # 计算每个分类在数据集中的概率:P(yi)

   self.doclength = len(trainset)

tempset = set()

  【tempset.add(word) for doc in trainset for word in doc 】 # Th成词典

  self.vocabulary= list(tempset)

  self.vocablen = len(self.vocabulary)

  self.calc_wordfreq(trainset) # 计算词频数据集

self.build_tdm() # 按分类累计向量空间的每维值:P(x|yi)

  3.cate_prob 函数:计算在数据集中每个分类的概率:P(yi)

def cate_prob(self,classVec):

self.labels = classVec

labeltemps = set(self.labels) # 获取全部分类

for labeltemp in labeltemps:

  # 统计列表中重复的分类:self.labels.count(labeltemp)

    self.Pcates【labeltemp】 = float(self.labels.count(labeltemp))/float(len(self.labels))

  4.calc_wordfreq 函数:生成普通的词频向量

# Th成普通的词频向量

def calc_wordfreq(self,trainset):

  self.idf = np.zeros(【1,self.vocablen】) # 1*词典数

  self.tf = np.zeros(【self.doclength,self.vocablen】) # 训练集文件数*词典数

  for indx in xrange(self.doclength): # 遍历所有的文本

    for word in trainset【indx】: # 遍历文本中的每个词

      self.tf【indx,self.vocabulary.index(word)】 +=1 # 找到文本的词在字典中的位置+1

    for signleword in set(trainset【indx】):

      self.idf【0,self.vocabulary.index(signleword)】 +=1

  5.build_tdm 函数:按分类累计计算向量空间的每维值:P(x|yi)

#按分类累计向量空间的每维值:P(x|yi)

def build_tdm(self):

  self.tdm = np.zeros(【len(self.Pcates),self.vocablen】) # 类别行*词典列 sumlist = np.zeros(【len(self.Pcates),1】) # 统计每个分类的总值

  for indx in xrange(self.doclength):

    self.tdm【self.labels【indx】】 += self.tf【indx】 # 将同一类别的词向量空间值加总

    # 统计每个分类的总值--是个标量

  sumlist【self.labels【indx】】= np.sum(self.tdm【self.labels【indx】】) self.tdm = self.tdm/sumlist # Th成 P(x|yi)

  6.map2vocab

函数:将测试集映射到当前词典

def map2vocab(self,testdata):

  self.testset = np.zeros(【1,self.vocablen】) for word in testdata:

  self.testset【0,self.vocabulary.index(word)】 +=1

  7.predict 函数:预测分类结果,输出预测的分类类别

def predict(self,testset):

  if np.shape(testset)【1】 != self.vocablen: # 如果测试集长度与词典不相等,退出程序

    print "输入错误"

    exit(0)

  predvalue = 0 # 初始化类别概率

  predclass = "" # 初始化类别名称

  for tdm_vect,keyclass in zip(self.tdm,self.Pcates):

    # P(x|yi) P(yi)

    temp = np.sum(testset*tdm_vect*self.Pcates【keyclass】) # 变量 tdm,计算最大分类值

    if temp > predvalue:

      predvalue = temp predclass = keyclass

  return predclass

  三. 算法改进

  为普通的词频向量使用 TF-IDF 策略,使之有能力修正多种偏差。

  4.calc_tfidf 函数:以 tf-idf 方式Th成向量空间:

# Th成 tf-idf

def calc_tfidf(self,trainset):

  self.idf = np.zeros(【1,self.vocablen】)

  self.tf = np.zeros(【self.doclength,self.vocablen】)

  for indx in xrange(self.doclength):

    for word in trainset【indx】:

      self.tf【indx,self.vocabulary.index(word)】 +=1

      # 消除不同句长导致的偏差

      self.tf【indx】 = self.tf【indx】/float(len(trainset【indx】))

        for signleword in set(trainset【indx】):

          self.idf【0,self.vocabulary.index(signleword)】 +=1

  self.idf = np.log(float(self.doclength)/self.idf)

  self.tf = np.multiply(self.tf,self.idf) # 矩阵与向量的点乘 tf x idf

  四. 评估分类结果

# -*- coding: utf-8 -*-

import sys import os

from numpy import * import numpyas np

from Nbayes_lib import *

dataSet,listClasses = loadDataSet() # 导入外部数据集

# dataset: 句子的词向量,

# listClass 是句子所属的类别 【0,1,0,1,0,1】

nb = NBayes() # 实例化

nb.train_set(dataSet,listClasses) # 训练数据集

nb.map2vocab(dataSet【0】) # 随机选择一个测试句

print nb.predict(nb.testset) # 输出分类结果

  分类结果

1

执行我们创建的朴素贝叶斯类,获取执行结果

目录
打赏
0
0
0
0
32
分享
相关文章
短视频到底如何推荐的?深度剖析视频算法推送原理详细且专业的解读-优雅草卓伊凡-【01】短视频算法推荐之数据收集
短视频到底如何推荐的?深度剖析视频算法推送原理详细且专业的解读-优雅草卓伊凡-【01】短视频算法推荐之数据收集
77 12
短视频到底如何推荐的?深度剖析视频算法推送原理详细且专业的解读-优雅草卓伊凡-【01】短视频算法推荐之数据收集
|
2月前
|
【📕分布式锁通关指南 04】redis分布式锁的细节问题以及RedLock算法原理
本文深入探讨了基于Redis实现分布式锁时遇到的细节问题及解决方案。首先,针对锁续期问题,提出了通过独立服务、获取锁进程自己续期和异步线程三种方式,并详细介绍了如何利用Lua脚本和守护线程实现自动续期。接着,解决了锁阻塞问题,引入了带超时时间的`tryLock`机制,确保在高并发场景下不会无限等待锁。最后,作为知识扩展,讲解了RedLock算法原理及其在实际业务中的局限性。文章强调,在并发量不高的场景中手写分布式锁可行,但推荐使用更成熟的Redisson框架来实现分布式锁,以保证系统的稳定性和可靠性。
71 0
【📕分布式锁通关指南 04】redis分布式锁的细节问题以及RedLock算法原理
基于贝叶斯优化的自适应马尔科夫链蒙特卡洛(Adaptive-MCMC)算法matlab仿真
本项目基于贝叶斯优化的自适应马尔科夫链蒙特卡洛(Adaptive-MCMC)算法,实现MATLAB仿真,并对比Kawasaki sampler、IMExpert、IMUnif和IMBayesOpt四种方法。核心在于利用历史采样信息动态调整MCMC参数,以高效探索复杂概率分布。完整程序在MATLAB2022A上运行,展示T1-T7结果,无水印。该算法结合贝叶斯优化与MCMC技术,通过代理模型和采集函数优化采样效率。
深度强化学习中SAC算法:数学原理、网络架构及其PyTorch实现
软演员-评论家算法(Soft Actor-Critic, SAC)是深度强化学习领域的重要进展,基于最大熵框架优化策略,在探索与利用之间实现动态平衡。SAC通过双Q网络设计和自适应温度参数,提升了训练稳定性和样本效率。本文详细解析了SAC的数学原理、网络架构及PyTorch实现,涵盖演员网络的动作采样与对数概率计算、评论家网络的Q值估计及其损失函数,并介绍了完整的SAC智能体实现流程。SAC在连续动作空间中表现出色,具有高样本效率和稳定的训练过程,适合实际应用场景。
649 7
深度强化学习中SAC算法:数学原理、网络架构及其PyTorch实现
理解CAS算法原理
CAS(Compare and Swap,比较并交换)是一种无锁算法,用于实现多线程环境下的原子操作。它通过比较内存中的值与预期值是否相同来决定是否进行更新。JDK 5引入了基于CAS的乐观锁机制,替代了传统的synchronized独占锁,提升了并发性能。然而,CAS存在ABA问题、循环时间长开销大和只能保证单个共享变量原子性等缺点。为解决这些问题,可以使用版本号机制、合并多个变量或引入pause指令优化CPU执行效率。CAS广泛应用于JDK的原子类中,如AtomicInteger.incrementAndGet(),利用底层Unsafe库实现高效的无锁自增操作。
167 0
理解CAS算法原理
基于分块贝叶斯非局部均值优化(OBNLM)的图像去噪算法matlab仿真
本项目基于分块贝叶斯非局部均值优化(OBNLM)算法实现图像去噪,使用MATLAB2022A进行仿真。通过调整块大小和窗口大小等参数,研究其对去噪效果的影响。OBNLM结合了经典NLM算法与贝叶斯统计理论,利用块匹配和概率模型优化相似块的加权融合,提高去噪效率和保真度。实验展示了不同参数设置下的去噪结果,验证了算法的有效性。
基于贝叶斯优化CNN-GRU网络的数据分类识别算法matlab仿真
本项目展示了使用MATLAB2022a实现的贝叶斯优化、CNN和GRU算法优化效果。优化前后对比显著,完整代码附带中文注释及操作视频。贝叶斯优化适用于黑盒函数,CNN用于时间序列特征提取,GRU改进了RNN的长序列处理能力。
【AI系统】布局转换原理与算法
数据布局转换技术通过优化内存中数据的排布,提升程序执行效率,特别是对于缓存性能的影响显著。本文介绍了数据在内存中的排布方式,包括内存对齐、大小端存储等概念,并详细探讨了张量数据在内存中的排布,如行优先与列优先排布,以及在深度学习中常见的NCHW与NHWC两种数据布局方式。这些布局方式的选择直接影响到程序的性能,尤其是在GPU和CPU上的表现。此外,还讨论了连续与非连续张量的概念及其对性能的影响。
162 3
OSPF的路由计算算法:原理与应用
OSPF的路由计算算法:原理与应用
169 4

热门文章

最新文章