1. 程式人生 > >機器學習回顧篇(5):樸素貝葉斯演算法

機器學習回顧篇(5):樸素貝葉斯演算法

1 引言

說到樸素貝葉斯演算法,很自然地就會想到貝葉斯概率公式,這是我們在高中的時候就學過的只是,沒錯,這也真是樸素貝葉斯演算法的核心,今天我們也從貝葉斯概率公式開始,全面擼一擼樸素貝葉斯演算法。

2 貝葉斯概率公式

2.1 聯合概率與全概率公式

定義1:完備事件組

${A_1} \cup {A_2} \cup \cdots \cup {A_n} = \Omega $,且${A_i} \cap {A_j} = \emptyset ,1 \le i \ne j \le n$,則稱${A_1},{A_2}, \cdots ,{A_n}$為一個完備事件組。

也就是說,如果${A_1},{A_2}, \cdots ,{A_n}$並集是完整的事件空間,且兩兩之間相互獨立(不相交),那麼${A_1},{A_2}, \cdots ,{A_n}$就是完備事件組。就像下圖中的事件${A_1},{A_2},{A_3},{A_4}$,他們之間兩兩不相交,但合起來(並集)就構成了一個完整的大灰色矩形框(完整的事件空間):

現在,如下圖所示,有一個事件$B$,$B$事件只有在事件${A_i}$發生的基礎上才會發生。注意,${A_i}$有可能是${A_1}$,也有可能是${A_2}$、${A_3}$、${A_4}$,而且${A_1}$、${A_2}$、${A_3}$、${A_4}$事件發生後發生$B$事件的概率可能不相等。

說到這裡又有兩個概念了:

先驗概率:有簡單統計分析可以獲得的概率,例如$P({A_i})$

條件概率:在事件${A_i}$發生的前提下,發生事件B的概率,表示為$P(B|{A_i})$。

聯合概率:事件${A_i}$和事件$B$同時發生的概率,表示為$P(B,{A_i})$。整個過程首先得保證${A_1}$發生,概率為$P({A_1})$,發生${A_1}$再發生$B$,概率是$P(B|{A_1})$,所以有:

\[P(B,{A_i}) = P({A_i})P(B|{A_i})\]

由上面幾個概念,就可以引申出全概率公式:

\[P(B) = \sum\limits_{i = 1}^n {P(B,{A_i})} = \sum\limits_{i = 1}^n {P({A_i})P(B|{A_i})} \]

這就是$B$事件的全概率公式,意思是如果有某個事件$B$的發生總是以另一事件${A_i}$作為前提(原因),那麼把各種前提事件${A_i}$下$B$發生的概率加起來就是事件$B$發生的概率。對上圖中的例子就有:

$P(B) = P({A_1})P(B|{A_1}) + P({A_2})P(B|{A_2}) + P({A_3})P(B|{A_3}) + P({A_4})P(B|{A_4})$

2.2 貝葉斯概率公式

從上面對全概率公式的介紹中我們知道了,事件$B$發生的概率就是在各個${A_i}$與事件$B$的聯合概率之和,也就是在各種不同${A_i}$情況下發生$B$事件概率之和。現在,我們考慮另一種場景:已知事件$B$發生了,問是由事件${A_i}$導致的概率,也就是$B$發生前提下發生事件${A_i}$的條件概率,即$P({A_i}|B)$,怎麼求呢?這就是貝葉斯概率公式解決的問題。

貝葉斯概率公式如下所示:

\[P({A_i}|B) = \frac{{P(B,{A_i})}}{{P(B)}}\]

也就是說,$B$發生前提下發生事件${A_i}$的條件概率等於事件${A_i}$、$B$的聯合概率與事件$B$發生的概率之間的商。繼續,我們將2.1節講過的聯合概率公式和全概率公式代入上面的貝葉斯概率公式,就得到了完整的貝葉斯公式:

\[P({A_i}|B) = \frac{{P(B,{A_i})}}{{P(B)}} = \frac{{P({A_i})P(B|{A_i})}}{{\sum\limits_1^n {P({A_i})P(B|{A_i})} }}\]

貝葉斯概率公式的作用:如果已知事件$B$發生了,去探求是某個原因${A_i}$導致這一結果發生的概率$P({A_i}|B)$,也就某個原因佔所有原因的比例。

為了更加透徹理解貝葉斯概率公式,我們現在來分析一個例子:

病樹的主人外出,委託鄰居澆水,假設已知如果不澆水樹死去的概率為$0.8$,若澆水,則樹死去的概率為$0.15$,有$0.9$的把握確定鄰居記得澆水。若主人回來時樹已經死去,求鄰居忘記澆水的概率?

我們用${A_1}$表示事件鄰居記得澆水,${A_2}$表示事件鄰居忘記澆水,用${B_1}$表示樹活著,用${B_2}$表示樹死了,那麼,已知的概率有:

鄰居記得澆水概率:$P({A_1}) = 0.9$

不澆水後樹死去的條件概率:$P({B_2}|{A_2}) = 0.8$

澆水後樹死去的條件概率:$P({B_2}|{A_1}) = 0.15$

鄰居忘記澆水的概率:$P({A_2}=1 - P({A_1}) = 0.1$

那麼,由全概率公式我們可以計算出樹活著的概率:

$P({B_2}) = P({A_1})P({B_2}|{A_1}) + P({A_2})P({B_2}|{A_2}) = 0.9 \times 0.15 + 0.1 \times 0.8 = 0.215$

進而用貝葉斯概率公式計算樹死去情況下鄰居忘記澆水的概率:

$P({A_2}|{B_2}) = \frac{{P({A_2})P({B_2}|{A_2})}}{{P({B_2})}} = \frac{{0.1 \times 0.8}}{{0.215}} = 0.372$

3 樸素貝葉斯分類演算法

3.1 單一屬性的樸素貝葉斯分類

我們通過一個例子來循序漸進地學習樸素貝葉斯演算法。

假設辦公室$6$成員工為程式設計師,$4$成為非程式設計師,程式設計師穿格子襯衫的概率是$0.7$,非程式設計師穿格子襯衫的概率是$0.1$,現在迎面走來一位穿格子襯衫的哥們,我們來判斷一下這位是否是程式設計師?

用${A_1}$表示穿格子襯衫,${A_2}$表示不穿給支襯衫,${B_1}$表示是程式設計師,${B_2}$表示非程式設計師,有:

$P({B_1}) = 0.6$

$P({B_2}) = 0.4$

$P({A_1}|{B_1}) = 0.7$

$P({A_1}|{B_2}) = 0.1$

由貝葉斯概率公式可以計算那麼穿格子襯衫的哥們是程式設計師和非程式設計師的概率分別是:

$P({B_1}|{A_1}) = \frac{{P({B_1})P({A_1}|{B_1})}}{{P({B_1})P({A_1}|{B_1}) + P({B_2})P({A_1}|{B_2})}} = \frac{{0.6 \times 0.7}}{{0.6 \times 0.7 + 0.4 \times 0.1}} = \frac{{0.42}}{{0.46}} \approx 0.91$

$P({B_2}|{A_1}) = \frac{{P({B_2})P({A_1}|{B_2})}}{{P({B_1})P({A_1}|{B_1}) + P({B_2})P({A_1}|{B_2})}} = \frac{{0.4 \times 0.1}}{{0.6 \times 0.7 + 0.4 \times 0.1}} = \frac{{0.04}}{{0.46}} \approx 0.09$

因為$P({B_1}|{A_1}) > P({B_2}|{A_1})$,所以,我們認為這位哥們是程式設計師。

對這位哥們是否是程式設計師進行分類的方法,就是樸素貝葉斯演算法。我們來總結一下這個過程:

(1)又已有資料統計分析出一些先驗概率和條件概率。就像上面的$P({B_1})$、$P({B_2})$、$P({A_1}|{B_1})$、$P({A_1}|{B_2})$。當然,這個例子中的這些概率是直接給出的,在真實應用中,這些概率需要通過統計分析得出。

(2)結合已知的先驗概率和條件概率,通過貝葉斯概率公式計算屬於各個分類的概率。在這一步驟中,有一個技巧,我們在回到上面計算兩個概率$P({B_1}|{A_1}) $、$ P({B_2}|{A_1})$的過程,發現分母不同,但是分支都是一樣的,因為都是計算穿格子襯衫的概率,所以,在實際演算法應用中,我們只需要計算分子,然後比較大小即可。

(3)比較屬於各個分類的概率,將資料劃分到概率最大的分類中。

3.2 多屬性的樸素貝葉斯分類

我想現在你已經對樸素貝葉斯演算法有些感覺了,那麼現在,我們系統的描述一下樸素貝葉斯演算法,並將其擴充套件到更加一般化的多維情況。

假設存在包含$m$個特徵,樣本容量為$n$的資料集$D = \{ (x_1^{(1)},x_2^{(1)}, \cdots ,x_m^{(1)},{y_1}),(x_1^{(2)},x_2^{(2)}, \cdots ,x_m^{(2)},{y_2}), \cdots ,(x_1^{(n)},x_2^{(n)}, \cdots ,x_n^{(n)},{y_n})\} $,${y}$是分類標籤,其取值${y_i} \in ({c_1},{c_2}, \cdots ,{c_K})$。

通過對資料集$D$的統計分析,我們可以獲得每個類別的先驗概率:

$P(Y = {c_k}),k = 1,2, \cdots ,K$

以及各分類條件下的不同特徵的條件概率:

$P({X_j} = {x_j}|Y = {c_k})$ (在$ {c_k}$類中第$j$維特徵取值為$ {x_j}$的概率)

樸素貝葉斯演算法有一個前提假設,那就是各特徵之間相互獨立,對於不同特徵組合下的條件概率有:

$P(X = x|Y = {C_k}) = P({X_1} = {x_1},{X_2} = {x_2}, \cdots ,{X_m} = {x_m}|Y = {C_k}) = \prod\limits_{j = 1}^m {P(} {X_j} = {x_j}|Y = {c_k})$

同時由全概率公式可得:

$P(X = x) = \sum\limits_{j = 1}^K {P(Y = {C_k}} )P({X_1} = {x_1},{X_2} = {x_2}, \cdots ,{X_m} = {x_m}|Y = {C_k}) = \sum\limits_{j = 1}^K {P(Y = {C_k}} )\prod\limits_{j = 1}^m {P(} {X_j} = {x_j}|Y = {c_k})$

當然,計算$P(X = x)$這一步其實是可以省略的,應該在貝葉斯概率公式中$P(X = x)$是作為分母,所有的$P(X = x)$都是一樣的,只需要計算分子就可以了。

之後通過貝葉斯 概率公式計算不同特徵組合下屬於不同分類概率:

$P(Y = {C_k}|X = x) = \frac{{P(Y = {C_k})P(X = x|Y = {C_k})}}{{P(X = x)}}$

將之前獲得的先驗概率、條件概率、全概率公式都用上,代入到上式中:

$P(Y = {C_k}|X = x) = \frac{{P(Y = {C_k})\prod\limits_{j = 1}^m {P(} {X_j} = {x_j}|Y = {c_k})}}{{\sum\limits_{j = 1}^K {P(Y = {C_k}} )\prod\limits_{j = 1}^m {P(} {X_j} = {x_j}|Y = {c_k})}}$

最後比較屬於各不同分類下的概率大小,取最大的一個分類概率,所以樸素貝葉斯分類演算法可以表示為:

$P(Y = {C_k}|X = x) = \underbrace {argmax}_{{C_k}}\frac{{P(Y = {C_k})\prod\limits_{j = 1}^m {P(} {X_j} = {x_j}|Y = {c_k})}}{{\sum\limits_{j = 1}^K {P(Y = {C_k}} )\prod\limits_{j = 1}^m {P(} {X_j} = {x_j}|Y = {c_k})}}$

上面說過,計算各分類下概率時分母$P(X = x)$都一樣,為節省計算量,可以分母,最終,樸素貝葉斯演算法可以表示為:

$P(Y = {C_k}|X = x) = \underbrace {argmax}_{{C_k}}P(Y = {C_k})\prod\limits_{j = 1}^m {P(} {X_j} = {x_j}|Y = {c_k})$

這也是樸素貝葉斯分類演算法的目標函式。

估計看了這麼多數學表達,很多人都有些暈了,來,我們繼續通過一個例子來解讀。有如下所示的一個數據集(純屬杜撰),每個員工有三個特徵屬性——是否穿格子襯衫(${x_1}$)、是否禿頂(${x_2}$)、是否戴眼鏡(${x_3}$),用來分類是否是程式設計師($y$),$1$表示肯定,$0$表示否定。現在要做的是對最後一條記錄進行分類,即判斷是否是程式設計師。

計算先驗概率:

$P(y = 0) = \frac{5}{{15}} = \frac{1}{3}$

$P(y = 1) = \frac{{10}}{{15}} = \frac{2}{3}$

不同分類下各特徵值的條件概率:

$P({x_1} = 0|y = 0) = \frac{3}{5},P({x_1} = 1|y = 0) = \frac{2}{5},P({x_1} = 0|y = 1) = \frac{2}{5},P({x_1} = 1|y = 1) = \frac{3}{5}$

$P({x_2} = 0|y = 0) = 1,P({x_2} = 1|y = 0) = 0,P({x_2} = 0|y = 1) = \frac{1}{{10}},P({x_2} = 1|y = 1) = \frac{9}{{10}}$

$P({x_3} = 0|y = 0) = \frac{3}{5},P({x_3} = 1|y = 0) = \frac{2}{5},P({x_3} = 0|y = 1) = \frac{1}{5},P({x_3} = 1|y = 1) = \frac{4}{5}$

通過貝葉斯概率公式計算最後一個樣本屬於不同分類的概率。

非程式設計師的概率:
$\eqalign{
  & P(y = 0|{x_1} = 1,{x_2} = 0,{x_3} = 1) = \frac{{P(y = 0)P({x_1} = 1,{x_2} = 0,{x_3} = 1|y = 0)}}{{P({x_1} = 1,{x_2} = 0,{x_3} = 1)}}  \cr
  &  = \frac{{\frac{1}{3} \times \frac{2}{5} \times 1 \times \frac{2}{5}}}{{\frac{1}{3} \times \frac{2}{5} \times 1 \times \frac{2}{5} + \frac{2}{3} \times \frac{3}{5} \times \frac{1}{{10}} \times \frac{4}{5}}} \approx 0.625 \cr} $

是程式設計師的概率:
$\eqalign{
  & P(y = 1|{x_1} = 1,{x_2} = 0,{x_3} = 1) = \frac{{P(y = 1)P({x_1} = 1,{x_2} = 0,{x_3} = 1|y = 1)}}{{P({x_1} = 1,{x_2} = 0,{x_3} = 1)}}  \cr
  &  = \frac{{\frac{2}{3} \times \frac{3}{5} \times \frac{1}{{10}} \times \frac{4}{5}}}{{\frac{1}{3} \times \frac{2}{5} \times 1 \times \frac{2}{5} + \frac{2}{3} \times \frac{3}{5} \times \frac{1}{{10}} \times \frac{4}{5}}} \approx 0.375 \cr} $

因為$P(y = 1|{x_1} = 1,{x_2} = 0,{x_3} = 1) \approx 0.625 > P(y = 0|{x_1} = 1,{x_2} = 0,{x_3} = 1) \approx 0.375$,該職工不是程式設計師的概率要大一些,所以判定該職工非程式設計師。

3.3 拉普拉斯平滑

還是上面的預測是否是程式設計師的資料集,假設有如下所示的一條資料,然後預測是否是程式設計師:

還是按照上面的步驟進行計算,於是有:
$\eqalign{
  & P(y = 0|{x_1} = 1,{x_2} = 1,{x_3} = 0) = \frac{{P(y = 0)P({x_1} = 1,{x_2} = 1,{x_3} = 0|y = 0)}}{{P({x_1} = 1,{x_2} = 1,{x_3} = 0)}}  \cr
  &  = \frac{{\frac{1}{3} \times \frac{2}{5} \times 0 \times \frac{3}{5}}}{{\frac{1}{3} \times \frac{2}{5} \times 0 \times \frac{3}{5} + \frac{2}{3} \times \frac{3}{5} \times \frac{9}{{10}} \times \frac{0}{5}}} = 0 \cr} $

 

等於$0$。仔細一看就明白了因為在所有非程式設計師的分類中,沒有一個禿頂的,即:

$P({x_2} = 1|y = 0) = 0$

所以造成貝葉斯概率公式計算式的分子是$0$。細細一想,這樣的話,只要是禿頂的,無論是否是穿格子襯衫、是否戴眼鏡,就一定是程式設計師。這樣真的沒問題嗎?結合實際來想,禿頂的也可能是大領導啊,只是因為訓練資料非程式設計師中沒有禿頂的,就認為非程式設計師一定不禿頂顯然不合適,而且也造成了是否穿襯衫、是否戴眼鏡這兩列資訊沒什麼用了(資訊丟失)。

這就是樸素貝葉斯演算法的先天缺陷:其他屬性攜帶的資訊被訓練集中未出現的屬性值“抹去”,卻預測出來的概率絕對為$0$。為了擬補這一缺陷,前輩們引入了拉普拉斯平滑的方法:對先驗概率的分子(劃分的計數)加$1$,分母加上類別數;對條件概率分子加$1$,分母加上對應特徵的可能取值數量。這樣在解決零概率問題的同時,也保證了概率和依然為$1$:

$P(c) = \frac{{|{D_c}|}}{{|D|}} \to P(c) = \frac{{|{D_c}| + 1}}{{|D| + N}}$

$P({x_i}|c) = \frac{{|{D_{{x_i}|c}}|}}{{|{D_c}|}} \to P({x_i}|c) = \frac{{|{D_{{x_i}|c}}| + 1}}{{|{D_c}| + {N_i}}}$

其中,$N$表示資料集中分類標籤,${N_i}$表示第$i$個屬性的取值類別數,${|D|}$樣本容量,${|{D_c}|}$表示類別$c$的記錄數量,${|{D_{{x_i}|c}}|}$表示類別$c$中第$i$個屬性取值為${x_i}$的記錄數量。

將這兩個式子應用到上面的計算過程中,就可以彌補樸素貝葉斯演算法的這一缺陷問題。

3.4 連續型屬性的概率計算

我們在上文中說到過的所有理論、案例都是圍繞離散型屬性來展開的,當屬性為離散型時,先驗概率和條件概率可以通過計算所在比例獲得,但現實應用中的資料往往並不都是離散型屬性也有可能是連續型,例如上面判斷程式設計師的例子,在是否戴眼鏡這一屬性改為眼睛近視度數,這個近視度數就是連續型,其取值可以取值範圍內的任意整數甚至浮點數。

當面對這種連續型的,又該怎麼做呢?

有兩種方法:

(1)通過劃分區間的方式離散化。

這種方法思想是將特徵屬性的取值範圍劃分為若干個區間,從而將連續型屬性離散化,例如眼睛近似度數是從0到1000度,那麼我們可以劃分為從0開始,區間長度為100的10個區間,這樣就講眼睛近視度數劃分為10個離散類別,達到離散化的目的。

但是這種離散化的方法難以把握劃分區間長度,如果劃分區間太小,劃分後的區間數量就會很多,每一個區間的記錄數量很少,可能導致對條件概率$P(X = x|y)$誤差不可靠。如果劃分區間長度太長,就導致部分資訊丟失,而且不同類別的記錄也有很大可能劃分到同一區間,導致分類不準確。

(2)通過概率密度函式計算概率。

這種方法首先需要假設該連續型屬性的取值服從某種概率分佈,然後通過訓練資料做引數估計,獲得分佈函式,在計算概率時,根據密度函式來計算概率。

通常,在多數情況下,我們假設資料是服從高斯分佈的,即$P({x_i}|c) \sim N({\mu _{c,i}},\sigma _{c,i}^2)$。其中,${\mu _{c,i}}$和$\sigma _{c,i}^2$分別是$c$類樣本在第$i$個屬性上取值的均值和方差,於是有:

$P({x_i}|c) = \frac{1}{{\sqrt {2\pi } {\sigma _{c,i}}}}{e^{ - \frac{{{{(x - {\mu _{c,i}})}^2}}}{{2\sigma _{c,i}^2}}}}$

4 總結

最後,對樸素貝葉斯分類演算法優缺點做一個總結。

優點:

(1)樸素貝葉斯分類演算法根源於貝葉斯概率公式,有很好的數學基礎,分類效率穩定。

(2)對小規模的資料表現很好,能個處理多分類任務,適合增量式訓練,尤其是資料量超出記憶體時,我們可以一批批的去增量訓練。

(3)對缺失資料不太敏感,演算法也比較簡單,常用於文字分類。

缺點:

(1)理論上,樸素貝葉斯模型與其他分類方法相比具有最小的誤差率。但是實際上並非總是如此,這是因為樸素貝葉斯模型給定輸出類別的情況下,假設屬性之間相互獨立,這個假設在實際應用中往往是不成立的,在屬性個數比較多或者屬性之間相關性較大時,分類效果不好。而在屬性相關性較小時,樸素貝葉斯效能最為良好。對於這一點,有半樸素貝葉斯之類的演算法通過考慮部分關聯性適度改進。

(2)需要知道先驗概率,且先驗概率很多時候取決於假設,假設的模型可以有很多種,因此在某些時候會由於假設的先驗模型的原因導致預測效果不佳。

(3)由於我們是通過先驗和資料來決定後驗的概率從而決定分類,所以分類決策存在一定的錯誤率。

(4)對輸入資料的表達形式很敏感。

參考:

https://www.cnblogs.com/pinard/p/6069267.html

https://www.jianshu.com/p/5953923f43f0

  &nbs