朴素贝叶斯分类实战:对文档进行分类
樸素貝葉斯分類最適合的場景就是文本分類、情感分析和垃圾郵件識別。其中情感分析和垃圾郵件識別都是通過文本來進行判斷。所以樸素貝葉斯也常用于自然語言處理 NLP 的工具。
sklearn 機器學習包
sklearn 的全稱叫 Scikit-learn,它給我們提供了 3 個樸素貝葉斯分類算法,分別是高斯樸素貝葉斯(GaussianNB)、多項式樸素貝葉斯MultinomialNB)和伯努利樸素貝葉斯(BernoulliNB)。
這三種算法適合應用在不同的場景下,我們應該根據特征變量的不同選擇不同的算法:
高斯樸素貝葉斯:特征變量是連續變量,符合高斯分布,比如說人的身高,物體的長度。
多項式樸素貝葉斯:特征變量是離散變量,符合多項分布,在文檔分類中特征變量體現在一個單詞出現的次數,或者是單詞的 TF-IDF 值等。
伯努利樸素貝葉斯:特征變量是布爾變量,符合 0/1 分布,在文檔分類中特征是單詞是否出現。
伯努利樸素貝葉斯是以文件為粒度,如果該單詞在某文件中出現了即為 1,否則為 0。而多項式樸素貝葉斯是以單詞為粒度,會計算在某個文件中的具體次數。
如身高、體重這種自然界的現象就比較適合用高斯樸素貝葉斯來處理。而文本分類是使用多項式樸素貝葉斯或者伯努利樸素貝葉斯。
什么是 TF-IDF 值呢?
TF-IDF 是一個統計方法,用來評估某個詞語對于一個文件集或文檔庫中的其中一份文件的重要程度。
詞頻 TF計算了一個單詞在文檔中出現的次數,它認為一個單詞的重要性和它在文檔中出現的次數呈正比。
逆向文檔頻率 IDF,是指一個單詞在文檔中的區分度。它認為一個單詞出現在的文檔數越少,就越能通過這個單詞把該文檔和其他文檔區分開。IDF 越大就代表該單詞的區分度越大。
所以 TF-IDF 實際上是詞頻 TF 和逆向文檔頻率 IDF 的乘積。這樣我們傾向于找到 TF 和 IDF 取值都高的單詞作為區分,即這個單詞在一個文檔中出現的次數多,同時又很少出現在其他文檔中。這樣的單詞適合用于分類。
TF-IDF 如何計算
些單詞可能不會存在文檔中,為了避免分母為 0,統一給單詞出現的文檔數都加 1。
舉個例子
假設一個文件夾里一共有 10 篇文檔,其中一篇文檔有 1000 個單詞,“this”這個單詞出現 20 次,“bayes”出現了 5 次。“this”在所有文檔中均出現過,而“bayes”只在 2 篇文檔中出現過。
針對“this”,計算 TF-IDF 值:
所以 TF-IDF=0.02*(-0.0414)=-8.28e-4。
針對“bayes”,計算 TF-IDF 值:
TF-IDF=0.005*0.5229=2.61e-3。
很明顯“bayes”的 TF-IDF 值要大于“this”的 TF-IDF 值。這就說明用“bayes”這個單詞做區分比單詞“this”要好。
如何求 TF-IDF
在 sklearn 中我們直接使用 TfidfVectorizer 類,它可以幫我們計算單詞 TF-IDF 向量的值。
在這個類中,取 sklearn 計算的對數 log 時,底數是 e,不是 10。
創建 TfidfVectorizer 的方法是:
當我們創建好 TF-IDF 向量類型時,可以用 fit_transform 幫我們計算,返回給我們文本矩陣,該矩陣表示了每個單詞在每個文檔中的 TF-IDF 值。
在我們進行 fit_transform 擬合模型后,我們可以得到更多的 TF-IDF 向量屬性,比如,我們可以得到詞匯的對應關系(字典類型)和向量的 IDF 值,當然也可以獲取設置的停用詞 stop_words。
現在想要計算文檔里都有哪些單詞,這些單詞在不同文檔中的 TF-IDF 值是多少呢?
首先我們創建 TfidfVectorizer 類:
如何對文檔進行分類(以下六個模塊只作示意)
1、基于分詞的數據準備,包括分詞、單詞權重計算、去掉停用詞; 2、應用樸素貝葉斯分類進行分類,首先通過訓練集得到樸素貝葉斯分類器,然后將分類器應用于測試集,并與實際結果做對比,最終得到測試集的分類準確率。
模塊 1:對文檔進行分詞
在準備階段里,最重要的就是分詞。那么如果給文檔進行分詞呢?英文文檔和中文文檔所使用的分詞工具不同。
在英文文檔中,最常用的是 NTLK 包。NTLK 包中包含了英文的停用詞 stop words、分詞和標注方法。
import nltk word_list = nltk.word_tokenize(text) # 分詞 nltk.pos_tag(word_list) # 標注單詞的詞性在中文文檔中,最常用的是 jieba 包。jieba 包中包含了中文的停用詞 stop words 和分詞方法。
import jieba
word_list = jieba.cut (text) # 中文分詞
模塊 2:加載停用詞表
我們需要自己讀取停用詞表文件,從網上可以找到中文常用的停用詞保存在 stop_words.txt,然后利用 Python 的文件讀取函數讀取文件保存在 stop_words 數組中。
模塊 3:計算單詞的權重
直接創建 TfidfVectorizer 類,然后使用 fit_transform 方法進行擬合,得到 TF-IDF 特征空間 features,你可以理解為選出來的分詞就是特征。我們計算這些特征在文檔上的特征向量,得到特征空間 features。
test_tf = TfidfVectorizer(stop_words=stop_words, max_df=0.5, vocabulary=train_vocabulary) test_features=test_tf.fit_transform(test_contents)這里 max_df 參數用來描述單詞在文檔中的最高出現率。假設 max_df=0.5,代表一個單詞在 50% 的文檔中都出現過了,那么它只攜帶了非常少的信息,因此就不作為分詞統計。
模塊 4:生成樸素貝葉斯分類器
我們將特征訓練集的特征空間 train_features,以及訓練集對應的分類 train_labels 傳遞給貝葉斯分類器 clf,它會自動生成一個符合特征空間和對應分類的分類器。
這里我們采用的是多項式貝葉斯分類器,其中 alpha 為平滑參數。為什么要使用平滑呢?因為如果一個單詞在訓練樣本中沒有出現,這個單詞的概率就會被計算為 0。為了解決這個問題,我們需要做平滑處理。
當 alpha=1 時,使用的是 Laplace 平滑。Laplace 平滑就是采用加 1 的方式,來統計沒有出現過的單詞的概率。
當 0<alpha<1 時,使用的是 Lidstone 平滑。對于 Lidstone 平滑來說,alpha 越小,迭代次數越多,精度越高。我們可以設置 alpha 為 0.001。
# 多項式貝葉斯分類器 from sklearn.naive_bayes import MultinomialNB clf = MultinomialNB(alpha=0.001).fit(train_features, train_labels)模塊 5:使用生成的分類器做預測
首先我們需要得到測試集的特征矩陣。
然后我們用訓練好的分類器對新數據做預測。
方法是使用 predict 函數,傳入測試集的特征矩陣 test_features,得到分類結果 predicted_labels。predict 函數做的工作就是求解所有后驗概率并找出最大的那個。
模塊 6:計算準確率
我們可以調用 sklearn 中的 metrics 包,在 metrics 中提供了 accuracy_score 函數,方便我們對實際結果和預測的結果做對比,給出模型的準確率。使用方法如下:
總結
一般來說 NTLK 包適用于英文文檔,而 jieba 適用于中文文檔。我們可以根據文檔選擇不同的包,對文檔提取分詞。這些分詞就是貝葉斯分類中最重要的特征屬性。基于這些分詞,我們得到分詞的權重,即特征矩陣。
練習
在這個鏈接下下載數據集:https://github.com/cystanford/text_classification
參考文獻
數據分析實戰45講
在線獲取文本進行文本處理
總結
以上是生活随笔為你收集整理的朴素贝叶斯分类实战:对文档进行分类的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 实战:关联规则挖掘
- 下一篇: python编程-迭代器(类,方法,继承