700字范文,内容丰富有趣,生活中的好帮手!
700字范文 > 朴素贝叶斯算法python sklearn实现_朴素贝叶斯算法优化与 sklearn 实现

朴素贝叶斯算法python sklearn实现_朴素贝叶斯算法优化与 sklearn 实现

时间:2020-06-25 08:46:20

相关推荐

朴素贝叶斯算法python sklearn实现_朴素贝叶斯算法优化与 sklearn 实现

进行拉普拉斯平滑运算后,我们运行程序,仍然得出了两个测试样本均属于非侮辱类的结果,这是为什么呢?

我们查看最终计算出的p0和p1会发现,他们的结果都是0,这又是为什么呢?

这是因为出现了另一个问题--下溢出

我们的概率运算中,所有参与运算的概率都太小了,小数相乘会使运算的积进一步减小,最终结果向下溢出超出了计算机浮点数的精度,就都会变成0

解决办法很自然的可以想到--将乘法运算转换为加法运算,但如何在保证算法正确性的前提下进行转换呢?

在代数中,ln(a*b)=ln(a)+ln(b),同时,自然对数可以保证运算趋势的正确性:

因此我们通过对数运算优化训练函数trainNB0与测试函数classifyNB:

def trainNB0(trainMap, results):

"""

朴素贝叶斯分类器训练函数

:param trainMap: 训练文档矩阵

:param results: 训练类别标签向量

:return:

p0Vect - 侮辱类的条件概率数组

p1Vect - 非侮辱类的条件概率数组

pAbusive - 文档属于侮辱类的概率

"""

dataListNum = len(trainMap)

vocabularysNum = len(trainMap[0])

""" 计算文档属于侮辱词概率 """

pAbusive = sum(results) / float(dataListNum)

p0Num = np.ones(vocabularysNum)

p1Num = np.ones(vocabularysNum)

p0Denom = 2.0

p1Denom = 2.0

""" 将所有行按是否是侮辱类分别叠加,统计各个词出现的次数 """

for i in range(dataListNum):

if results[i] == 1:

p1Num += trainMap[i]

p1Denom += sum(trainMap[i])

else:

p0Num += trainMap[i]

p0Denom += sum(trainMap[i])

""" 计算概率 """

p1Vect = np.log(p1Num / p1Denom)

p0Vect = np.log(p0Num / p0Denom)

return p0Vect, p1Vect, pAbusive

def classifyNB(vec2Classify, p0Vec, p1Vec, pClass1):

"""

朴素贝叶斯分类器分类函数

:param vec2Classify: 待分类的词条数组

:param p0Vec: 侮辱类的条件概率数组

:param p1Vec: 非侮辱类的条件概率数组

:param pClass1: 文档属于侮辱类的概率

:return: 是否属于侮辱类,0. 不属于,1. 属于

"""

p0 = sum(vec2Classify * p0Vec) + np.log(1.0 - pClass1)

print("p0: ", p0)

p1 = sum(vec2Classify * p1Vec) + np.log(pClass1)

print("p1: ", p1)

if p1 > p0:

return 1

else:

return 0

最终我们得到了正确的结果:

p0: -7.694848072384611

p1: -9.826714493730215

['love', 'my', 'dalmation'] 属于非侮辱类

p0: -7.20934025660291

p1: -4.702750514326955

['stupid', 'garbage'] 属于侮辱类

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。