使用贝叶斯规则进行垃圾邮件分类

2017-05-03  本文已影响0人  xiaowenjie21

最近开始学习机器学习算法, 比如常用的贝叶斯规则, 常用来对做文本分类:作者归属, 垃圾邮件检测等。这里我使用python 做了一个分类器。

说下思路:1.准备训练集于测试集,包含垃圾邮件与普通邮件。2.使用jieba对训练集数据分词, 得到每封邮件【word1 word2, word3 word4,...]对 分类标签labels [1,0,....]。3.使用TF算法抽取词频高的词语。4.转换器转换高维文本向量。5.构造分类器 6.测试数据集

涉及到的知识点:朴素贝叶斯分类规则, 比如一封邮件。我们需要知道该邮件出现的单词,在垃圾邮件与正常邮件中的占比。A词占比 pw_s = spamEmail[word]/spamEmailFileLen (pw_s表示在垃圾邮件中该单词的出现的概率) spamEmail[word] 在所有垃圾邮件中该词的占比概率。spamEmailFilelen垃圾邮件长度 。然后计算pw_n = normEmail[word]/normEmailFileLen (pw_n表示普通邮件中该单词的概率),后面是一样。然后使用贝叶斯规则计算ps_w 也就是如果word出现,是垃圾邮件的概率为多少. ps_w = pw_s / pw_s+pw_n (贝叶斯公式) .

当得到所有的词概率后,进行全概率计算 ps_w1 *ps_w2*ps_w3.... 得到ps_w 然后pn_w1=(1-ps_w1)类似上面的公式得到总概率 pn_w.计算 p = ps_w/ps_w+pn_w 就能够得到该邮件是垃圾邮件的概率了。

python关键代码:

1.设计分词函数

def   get_word_list(content,wordsList,stopList,file_words_list):

#分词结果放入res_list并返回单词列表

res_list=list(jieba.cut(content))

foriinres_list:

ifinot instopListandi.strip()!=''andi!=None:

ifinot inwordsList:

wordsList.append(i)

#对普通邮件进行分词,将分词结果放入words_list中,每封邮件以逗号分隔每个词以 空格隔开

normal_files=os.listdir("data/normal")

spam_files=os.listdir("data/spam")

wordsList=[]

file_words_list=[]

spam_words_list=[]

forfinnormal_files:

wordsList.clear()

forlineinopen("data/normal/"+f):

rule=re.compile(r"[^\u4e00-\u9fa5]")

line=rule.sub("",line)

get_word_list(line,wordsList,stopList,file_words_list)

file_words_list.append(' '.join(wordsList))

#垃圾邮件同上

#拿到训练集与标签后,可以进行特征提取了。

#文本向量化,提取重要词变量最大出现的概率为50%

vectorizer=TfidfVectorizer(sublinear_tf=True,max_df=0.5)

features_train_transformed=vectorizer.fit_transform(features_train)

features_test_transformed=vectorizer.transform(features_test)

#根据训练集选择合适的特征

#进行特征转换

selector=SelectPercentile(f_classif,percentile=10)

selector.fit(features_train_transformed,labels_train)

features_train_transformed=selector.transform(features_train_transformed).toarray()

features_test_transformed=selector.transform(features_test_transformed).toarray()

###邮件统计信息

print("no. of spam training emails:",sum(labels_train))

print("no. of norm training emails:",len(labels_train)-sum(labels_train))


#进行预测

clf=GaussianNB()

clf.fit(features_train_transformed,labels_train)

pred=clf.predict(features_test_transformed)

#acc计算准确率

acc=accuracy_score(labels_test,pred)


上一篇下一篇

猜你喜欢

热点阅读