本章的最后一个例子非常有趣。我们前面介绍了朴素贝叶斯的两个实际应用的例子,第一个 例子是过滤网站的恶意留言,第二个是过滤垃圾邮件。分类还有大量的其他应用。我曾经见过有 人使用朴素贝叶斯从他喜欢及不喜欢的女性的社交网络档案学习相应的分类器,然后利用该分类 器测试他是否会喜欢一个陌生女人。分类的可能应用确实有很多,比如有证据表示,人的年龄越 大 ,他所用的词也越好。那 么 ,可以基于一个人的用词来推测他的年龄吗?除了年龄之外,还能 否推测其他方面?广告商往往想知道关于一个人的一些特定人口统计信息,以便能够更好地定向 推销广告。从哪里可以获得这些训练数据呢?事 实 上 ,互联网上拥有大量的训练数据。几乎任一 个能想到的利基市场
0
都 有专业 社区,很多人会认为自己属于该社区。4.3.1
节中的斑点犬爱好者网站就是一个非常好的例子。
在这个最后的例子当中,我们将分别从美国的两个城市中选取一些人,通过分析这些人发布的 征婚广告信息,来比较这两个城市的人们在广告用词上是否不同。如果结论确实是不同,那么他们 各自常用的词是哪些?从人们的用词当中,我们能否对不同城市的人所关心的内容有所了解?
.
示例:使用朴素贝叶斯来发现地域相关的用词!
j • - , . • . - ■ • - • , • ^ • . • ■ …… > >‘、 I
⑴ 收 集 数 据 :从尺
83
源收集内容,这里需要对尺88
源构建一个接口。(2)
准备数据:将文本文件解析成词条向量。(3)
分 析数据:检查词条确保解析的正确性。(4)
训练算 法 :使用我们之前建立的(^311^
犯0(>
函数。(5)
测试算法:观察错误率,确保分类器可用。可以修改切分程序,以降低错误率,提高 分类结果。(6)
使 用 算 法 :构建一个完整的程序,封装所有内容。给定两个尺88
源 ,该程序会显示最 常用的公共词。下面将使用来自不同城市的广告训练一个分类器,然后观察分类器的效果。我们的目的并不 是使用该分类器进行分类,而是通过观察单词和条件概率值来发现与特定城市相关的内容。
4 . 7 . 1
收 集 数 据 : 导 入R S S
源接下来要做的第一件事是使用
?7&£^
下载文本。幸 好 ,利用& 8 8
,这些文本很容易得到。现 在所需要的是一个尺88
阅读器。UniversalFeed ?8
巧6
邊?711
伽中最常用的尺88
程 序库。①利 基“ 丨也“ 是指针对企业的优势细分出来的市场,这个市场不大,而且没有得到令人满意的服务。产品推进这 个市场,有盈利的基础。在这里特指针对性和专业性都很强的产品。也就是说,利基是细分市场没有被服务好的 群体。一译者 注
4 . 7
示 例 :使 用 朴素贝 叶斯分 类器 从个 人广 告中 获取 区域 倾向69
top30Words = calcMostFre q( vo ca bL is t,fullText) f o r p a i r W in t o p 3 0 W o r d s :
70
第4
章 基 于 概 率 论 的 分 类 方 法 :朴素贝叶斯tra in M a t. append(bagOfWords2VecMN(vocabList, do cL ist [docIndex])) tra in C la s s e s.append(classList[docIndex])
pOV,plV,pSpam = trainN B 0(a rra y (tra in M a t),a rra y (tra in C la s s e s )) errorCount = 0
fo r docIndex in te s tS e t:
wordVector = bagOfWords2VecMN(vocabList, d o c L is t[docIndex]) i f cla ssifyN B (a rra y {wordVector),pOV,plV,pSpam) ! = \
cla ssL ist[d o c In d e x] : errorCount += 1
p r in t 1 the e rro r ra te is : ' , flo a t(e rro rC o u n t)/le n (te s tS e t) re tu rn vocabList,pO V,plv
上述代码类似程序清单4-5中的函数3£>矹7 6 3 “ >,不过添加了新的功能。代码中引人了一个 称为停用词表(
stop word list),
目前可以找到许多停用词表(在本书写作期间,http://www.ranks.nU resources/stopwords.html
上有一个很好的多语言停用词列表)。将程序清单4_6中的代码加人到bayes . 口^^文件之后,可以通过输入如下命令在?>^011中进行 测 试 :
>>> reload(bayes)
<module 1bayes1 from 'bayes.p y '>
>>>ny=feedparser.parse{ 1 h t t p://n e w y o r k .c r a ig s lis t.o rg /s tp /in d e x .r s s ')
> > > s f = f e e d p a r s e r .p a r s e ( 1 h t t p :/ / s f b a y . c r a i g s l i s t ■o r g / s t p / i n d e x ■r s s ')
>>> v o c a b L i s t ,p S F ,p N Y = b a y e s .l o c a l W o r d s ( n y , s f ) the e rro r ra te is : 0.1
>>> vocabList, pSF, pNY=bayes. localWords(ny,sf) the e rro r ra te is : 0.35
为了得到错误率的精确估计,应该多次进行上述实验,然后取平均值。这里的错误率要远髙 于垃圾邮件中的错误率。由于这里关注的是单词概率而不是实际分类,因此这个问题倒不严重。
可以通过函数0301风03七? 1 6 9()改变要移除的单词数目,然后观察错误率的变化情况。
4 . 7
示 例 :使 用朴 素 贝叶 斯 分类器 从个 人广 告中获 取区 域倾 向71
72
第4
章 基 于 概 率 论 的 分 类 方 法 : 朴 素 贝 叶 斯最后输出的单词很有意思。值得注意的现象是,程序输出了大量的停用词。移除固定的停用 词看看结果会如何变化也十分有趣。依我的经验来看,这 样 做 的 话 ,分类错误率也会降低。