适用问题:多类分类
模型类型:生成模型
模型特点:特征与类别的联合概率分布,条件独立假设。
学习策略:极大似然估计,极大后验概率估计或者损失函数为目标函数的最小化
学习的试试函数:对数似然损失
学习算法:概率计算公式,EM算法
原理:朴素贝叶斯分类(NBC)是以贝叶斯定理为基础并且假设特征条件之间相互独立的方法,先通过已给定的训练集,以特征词之间独立作为前提假设,学习从输入到输出的联合概率分布,再基于学习到的模型,输入求出使得后验概率最大的输出。
设有样本数据集,对应样本数据的特征属性集
类变量为,即可以分为类别。其中相互独立且随机,则的先验概率,的后验概率,由朴素贝叶斯算法可得,后验概率可以由先验概率、证据、类条件概率计算出:
朴素贝叶斯基于各特征之间相互独立,在给定类别为y的情况下,上式可以进一步表示为下式:
由以上两式可以计算出后验概率为:
由于的大小是固定不变的,因此在比较后验概率时,只比较上式的分子部分即可。因此可以得到一个样本数据属于类别的朴素贝叶斯计算如下图所示:
朴素贝叶斯是一种简单但是非常强大的线性分类器。对于训练数据集首先基于特征条件独立假设学习输入输出的联合概率分布;之后基于此模型对给定的输入X,利用贝叶斯定理求出后验概率(期望风险最小化)最大的X。它在垃圾邮件分类,疾病诊断中都取得了很大的成功。它只所以称为朴素,是因为它假设特征之间是相互独立的。数学原理:在X情况下,Y产生的概率。
#1、根据训练集创建朴素贝叶斯分类器
#1.1、生成类别的概率
#计算训练集合D中类别出现的概率,即P{c_i}
#输入:trainData 训练集,类型为数据框
strClassName 指明训练集中名称为strClassName列为分类结果
#输出:数据框,P{c_i}的集合,类别名称|概率(列名为 prob)
class_prob <- function(trainData, strClassName){
#训练集样本数
length.train <<- nrow(trainData)
#nrow返回行数,统计频数
dTemp <- ddply(trainData, strClassName, “nrow”)
#计算概率
dTemp <- ddply(dTemp, strClassName, mutate, prob = nrow/length.train)
dTemp[,-2]
}
#1.2、生成每个类别下,特征取不同值的概率
#计算训练集合D中,生成每个类别下,特征取不同值的概率,即P{fi|c_i}
#输入:trainData 训练集,类型为数据框
#输出:数据框,P{fi|c_i}的集合,类别名称|特征名称|特征取值|概率(列名为 prob)
feature_class_prob <- function(trainData, strClassName){
data.melt <- melt(trainData,id=c(strClassName))
aa <- ddply(data.melt, c(strClassName,“variable”,“value”), “nrow”)
bb <- ddply(aa, c(strClassName,“variable”), mutate, sum = sum(nrow), prob = nrow/sum)
colnames(bb) <- c(“class.name”,
“feature.name”,
“feature.value”,
“feature.nrow”,
“feature.sum”,
bb[,c(1,2,3,6)]
}
#以上创建完朴素贝叶斯分类器
#使用生成的朴素贝叶斯分类器进行预测P{fi|c_i}
#输入:oneObs 数据框,待预测的样本,格式为 特征名称|特征值
#输出:数据框,待预测样本的分类对每个类别的概率,类别名称|后验概率(列名为 prob)
pre_class <- function(oneObs, pc,pfc){
colnames(oneObs) <- c(“feature.name”, “feature.value”)
colnames(pc) <- c(“class.name”,“prob”)
colnames(pfc) <- c(“class.name”,“feature.name”,“feature.value”,“prob”)
feature.all <- join(oneObs,pfc,by=c(“feature.name”,“feature.value”),type=“inner”)
feature.prob <- ddply(feature.all,.(class.name),summarize,prob_fea=prod(prob)) #prod为连乘函数
#取出类别的概率
class.all <- join(feature.prob,pc,by=“class.name”,type=“inner”)
#输出结果
ddply(class.all,.(class.name),mutate,pre_prob=prob_fea*prob)[,c(1,4)]
}
#3、数据测试
train.apple <-data.frame(
oneObs<-data.frame(