项目背景:
★ 我们公司的应用有个需求是对用户发表的评论进行过滤,除了人工审核干预以外,我们还需要自动化检测评论来规避这些行为,为此我们研究贝叶斯算法,写了评论检测的项目用于过滤垃圾评论。
贝叶斯算法介绍
贝叶斯分类算法是统计学的一种分类方法,它是一类利用概率统计知识进行分类的算法。在许多场合,朴素贝叶斯(Naïve Bayes,NB)分类算法可以与决策树和神经网络分类算法相媲美,该算法能运用到大型数据库中,而且方法简单、分类准确率高、速度快。 (摘自百度)
朴素贝叶斯算法
朴素贝叶斯法(Naive Bayes)是基于贝叶斯定理与特征条件独立假设的分类方法。对于给定的训练数据集,首先基于特征条件独立假设学习输入/输出的联合概率分布;然后基于此模型,对给定的输入 xx ,利用贝叶斯定理求出后验概率最大的输出 yy 。
设每个数据样本用一个n维特征向量来描述n个属性的值,即:X={x1,x2,…,xn},假定有m个类,分别用C1, C2,…,Cm表示。给定一个未知的数据样本X(即没有类标号),若朴素贝叶斯分类法将未知的样本X分配给类Ci,则一定是
P(Ci|X)>P(Cj|X) 1≤j≤m,j≠i
根据贝叶斯定理,由于P(X)对于所有类为常数,最大化后验概率P(Ci|X)可转化为最大化先验概率P(X|Ci)P(Ci)。如果训练数据集有许多属性和元组,计算P(X|Ci)的开销可能非常大,为此,通常假设各属性的取值互相独立,这样
先验概率P(x1|Ci),P(x2|Ci),…,P(xn|Ci)可以从训练数据集求得。
根据此方法,对一个未知类别的样本X,可以先分别计算出X属于每一个类别Ci的概率P(X|Ci)P(Ci),然后选择其中概率最大的类别作为其类别。
朴素贝叶斯算法成立的前提是各属性之间互相独立。当数据集满足这种独立性假设时,分类的准确度较高,否则可能较低。另外,该算法没有分类规则输出。
我们项目中应用的正是朴素贝叶斯算法
分词算法
我测试了多个分词算法,包括
Ansj,FudanNLP,HanLP,IKAnalyzer,Jcseg,Jieba,MMSeg4j,Paoding,Smartcn,Stanford
经过仔细对比,最后采用了Hanlp的NLP分词,因为和Hanlp对中文的分词效果比较接近我们的场景。
NLP分词默认模型训练来自9970
万字的大型综合语料库,是已知范围内全世界最大的中文分词语料库,该分词的效果是我们测试了6,7种分词算法里最优秀的,也是最适合我们评论分词的场景的。
项目实现:
一、训练过程
1.把悦读的评论库作为训练模型,每周固定时间从悦读数据库拉取数据到本地,按不当评论和正常评论存储到本地
2.用Hanlp的NLP分词对拉取到本地的评论进行分词
3.对分词的结果用朴素贝叶斯算法计算概率(贝叶斯算法是机器学习常用的一种算法)
在我们的场景下公式可以转化为:
p代表有不当词语,评论为不当评论的概率
p1代表不当评论的基础概率
p2代表正常评论的基础概率
p3代表不当评论的条件概率
p4代表正常评论的条件概率
根据公式可得:p=(p1×p3)/(p1×p3+p2×p4)
4.把计算后的概率存到ElasticSearch数据库
流程图如下:
二、人工干预概率
如果训练出来的词语概率有不准确的情况,会导致线上评论被误杀,学生无法发表正常的评论,为此我们增加了一个功能去单独为这个词语设置概率,操作步骤如下:
1.设置概率保存到ES里
2.读取时优先读取人工设置的概率
3.如果没有人工概率再读取训练的概率。
三、检测过程
1.对检测的评论进行分词,得到一个分词后的词语集合
2.查询ES里面这些词语的概率
3.通过复合概率公式或者平均概率公式计算不当评论的概率(本次项目使用的是平均概率公式,也可以切换到复合概率公式)
复合概率公式: P(A|t1 ,t2, t3……tn)=(P1P2……PN)/[P1P2……PN+(1-P1)(1-P2)……(1-PN)]
平均概率公式:P(A|t1 ,t2, t3……tn)=(P1+P2+……+PN)/N
当P(A|t1 ,t2, t3……tn) 超过预定阈值时,就可以判断为垃圾评论
假设有一句评论:这是一个美好的下午,有个王者在打荣耀
分词后从ES查询的概率分别为:
{
"荣耀": 0.76527333,
"王者": 0.9477534,
"下午": 0.6597938,
"美好": 0.26188296
}
根据平均概率公式可以算出
p=0.6586759
根据复合概率公式可以算出
p=0.9760163
这时候我们需要判定这个概率到底是否属于不当评论,这里就需要一个阀值,阀值怎么确认呢?我们接下来就要讲到这个计算。
检测的流程图如下:
四、阀值的计算
阀值关系到最终不当评论的结果判定,所以计算这个需要谨慎再谨慎,我耗费了整整半个月的时间来改进算法,以及确定这个阀值。
到底如何确定阀值呢,我是通过对线上的几十万评论进行检测确定的
首先我们线上的评论已经由人工确定了几个分类(删除,屏蔽,不通过,正常,未审核),我这边要做的就是对这些不同种类的评论进行检测,删除和屏蔽状态的是不当评论,不通过和正常的是正常的评论(这里我们的审核机制是,如果不是特别好的评论都归纳为不通过评论,所以不通过评论也是正常的)
对这些评论分别检测以后我们可以得到一个不当评论的漏检率,正常评论的误报率,我会把阀值设定在(0-1之间,每隔0.03概率检测一次),相当于检测了30次左右,在这30次中,不当评论的漏检率越低越好,正常评论的误报率越低越好,最终得出在阀值为0.4时效果比较好:
正常评论误杀率为:0.068208896,不当评论漏检率为:0.11396843
这个结果是平均概率公式的结果,复合概率公式会有些差异。最后鉴于我们有人工的参与,不当评论漏检率可以允许高一点,正常评论误杀率要低一点,所以我最后还是选择了概率阀值:0.49,正常评论误杀率为0.03.
总结:
(2024.9.19)人工智能是未来的趋势,这是18年做的项目了。目前的人工智能已经转战大模型,这种算法都是小case了,不过了解一下这种算法也好,因此我还是把这篇博客保留下来了
标签:Ci,概率,检测,贝叶斯,算法,评论,分词 From: https://www.cnblogs.com/leecoder5/p/18420710