跳轉到

2.4 獨立性與貝氏定理#

本節目標#

  • 分清楚「獨立」與「互斥」——兩個常被混為一談、實際上幾乎相反的概念
  • 認識 Bayes 1763 年遺稿與其引發的千年難題(逆機率問題)
  • 推導貝氏定理,掌握先驗、概似、後驗三個角色
  • 用百萬人模擬重現「疾病篩檢悖論」,解釋基率謬誤

獨立 vs 互斥:兩個相反的概念#

互斥#

\(A \cap B = \varnothing\) :兩件事不能同時發生。 \(A\) 的發生排除了 \(B\) ——這是一種強烈的依賴。若兩事件都非零機率,互斥時 \(P(A \mid B) = 0 \ne P(A)\) 。

獨立#

\(A\) 的發生不提供任何關於 \(B\) 的資訊:

$$ P(A \mid B) = P(A) \quad \Longleftrightarrow \quad P(A \cap B) = P(A)\, P(B)

$$ (右式是左式代入條件機率定義的結果,也是定義上更常用的形式,因為它不要求 \(P(B) > 0\) 。)

動手:用模擬分清兩者#

import rstatistics as r

g = r.set_seed(3)
N = 1_000_000
d = g.sample_from(list(range(1, 7)), size=N, replace=True)

# 事件 A:偶數 {2,4,6};事件 B:奇數 {1,3,5}(兩事件互斥)
A = [x % 2 == 0 for x in d]
B = [x % 2 == 1 for x in d]
AB = [a and b for a, b in zip(A, B)]

pA, pB, pAB = sum(A)/N, sum(B)/N, sum(AB)/N
print(f"P(A)={pA:.4f}  P(B)={pB:.4f}  P(A∩B)={pAB:.4f}")
print(f"互斥:P(A∩B) = {pAB:.4f} ≈ 0")
print(f"若獨立應有 P(A)P(B) = {pA*pB:.4f} ≠ 0 → 互斥但絕不獨立!")

# 事件 C:{2,3}。P(C)=1/3, P(A∩C)=P({2})=1/6 = P(A)P(C)
C = [x in (2, 3) for x in d]
AC = sum(1 for a, c in zip(A, C) if a and c)/N
pC = sum(C)/N
print(f"\nA 與 C:P(A)P(C) = {pA*pC:.4f},  P(A∩C) = {AC:.4f}  → 相等,獨立")

輸出:

P(A)=0.4997  P(B)=0.5003  P(A∩B)=0.0000
互斥:P(A∩B) = 0.0000 ≈ 0
若獨立應有 P(A)P(B) = 0.2500 ≠ 0 → 互斥但絕不獨立!
A 與 C:P(A)P(C) = 0.1667,  P(A∩C) = 0.1663  → 相等,獨立

口訣:互斥 = 互相排斥(依賴得很徹底);獨立 = 互不告知(毫無關係)。 兩個正機率事件不可能既互斥又獨立。


歷史:1763 年 Bayes 的遺稿與「逆機率問題」#

18 世紀的機率論很會「正向」算:知道袋子裡紅白球比例,算抽到紅的機率。但科學真正要問的是逆向:看到數據之後,原因的機率該怎麼更新?

  • John Canton 與望遠鏡時代的難題:天文學家觀測到一系列數據,「如果某假說為真,出現這些數據的機會有多大」會算,但「看到這些數據後假說有多可信」不會算。這個逆機率問題(inverse probability problem)困擾了整個世紀。
  • Thomas Bayes(約 1701–1761),英國長老教會牧師、業餘數學家,生前默默無聞。他解出逆問題的核心公式,但論文未曾發表。1763 年,友人 Richard Price 在他的遺物中發現手稿,整理為 An Essay towards solving a Problem in the Doctrine of Chances 投稿到倫敦皇家學會哲學學報,並親自附上應用(用牛頓力學未知參數說明上帝存在之論證,今日看來別有時代趣味)。
  • 諷刺的是,我們今天寫的「貝氏定理」的乾淨形式,更多歸功於Laplace(1774 年起)的獨立推導與大力推廣;「貝氏」之名是後人追認。而貝氏方法成為主流要等到 20 世紀電腦出現——先驗分布、積分、馬可夫鏈蒙地卡羅(MCMC),樣樣都吃算力。今天從垃圾郵件過濾到 AlphaGo,全是這封遺稿的後代。

貝氏定理:機率的「換向」工具#

從條件機率的定義出發, \(P(AB)\) 有兩種寫法:

$$ P(AB) = P(A \mid B)\, P(B) = P(B \mid A)\, P(A)

$$ 兩邊同除 \(P(B)\) :

$$ P(A \mid B) = \frac{P(B \mid A)\, P(A)}{P(B)}

$$ 再對分母用全機率法則( \(A\) 與 \(A^c\) 是一個分割),得到最常用的形式:

$$ P(A \mid B) = \frac{P(B \mid A)\, P(A)}{P(B \mid A)\, P(A) + P(B \mid A^c)\, P(A^c)}

$$ 三個角色,用診斷問題的語言命名:

名稱 數學 診斷語言
先驗(prior) \(P(A)\) 看檢查之前,患病的機率(= 盛行率)
概似(likelihood) \(P(B \mid A)\) 若患病,檢查呈陽性的機率(= 靈敏度)
後驗(posterior) \(P(A \mid B)\) 檢查陽性後,患病的機率

貝氏定理就是學習的數學:後驗 = 先驗被數據(概似)更新後的結果。明天的新資訊來了,今天的後驗就變成明天的先驗,如此迭代。


疾病篩檢悖論#

理論計算#

設定:盛行率 \(P(D) = 1/1000\) ;靈敏度 \(P(+ \mid D) = 0.99\) ;特異度 99%,即健康者誤報率 \(P(+ \mid D^c) = 0.01\) 。代入貝氏定理:

$$ P(D \mid +) = \frac{0.99 \times 0.001}{0.99 \times 0.001 + 0.01 \times 0.999} = \frac{0.00099}{0.01098} \approx 0.0902

$$ 陽性之後,真正患病的機率只有約 9%。 憑直覺答 99% 的人,是把「 \(P(+ \mid D)\) 」(患病時陽性的機率)與「 \(P(D \mid +)\) 」(陽性時患病的機率)搞混了——條件機率的方向不能顛倒,這正是 Bayes 1763 年要解的問題。

直覺解釋:把 100 萬人排出來#

抽象公式記不住?想像替 100 萬人篩檢:

人數 陽性人數
患者(0.1%) 1,000 990(靈敏度 99%)
健康(99.9%) 999,000 9,990(誤報 1%)
合計 1,000,000 10,980

陽性共 10,980 人,其中真正的患者只有 990 人:

$$ 990 / 10980 \approx 9\%

$$ 「把母群體換成一個大整數」這個技巧叫自然頻率(natural frequencies),是 Gigerenzer 等人提倡的、對抗基率謬誤最有效的教法——醫生和法官聽得懂頻率,卻常被百分比絆倒。

基率謬誤(base rate fallacy)#

錯誤的根源是忽略先驗(基率):只看「檢查很準(99%)」就貿然回答,忘了患病基率只有千分之一。基率越極端,檢查的「表面準度」與後驗的落差越大。同樣一個 99% 準的檢查:

  • 盛行率 1/1000 → 後驗約 9%
  • 盛行率 1/100 → 後驗約 50%
  • 盛行率 1/10 → 後驗約 91.7%

實務啟示:低盛行率時的單次陽性不足為憑,所以公共衛生上對罕見疾病的陽性要做第二次獨立複檢——用貝氏定理迭代,第一次的後驗 9% 成為先驗,複檢再陽性後驗跳到約 91%。

動手:百萬人模擬驗證#

import rstatistics as r

g = r.set_seed(42)
N = 1_000_000

# 疾病篩檢:盛行率 1/1000,靈敏度 0.99,特異度 0.99
prev, sens, spec = 1/1000, 0.99, 0.99

# 每人先決定是否患病,再決定篩檢結果
u = g.runif(N)
sick = [1 if x < prev else 0 for x in u]

u2 = g.runif(N)
pos = 0
pos_sick = 0
for s, t in zip(sick, u2):
    threshold = sens if s == 1 else 1 - spec
    if t < threshold:
        pos += 1
        if s == 1:
            pos_sick += 1

print(f"檢測陽性的比例           = {pos/N:.5f}")
print(f"陽性中真正患病的比例     = {pos_sick/pos:.5f}")
print(f"貝氏定理理論值           = {(0.99*0.001)/(0.99*0.001+0.01*0.999):.5f}")

輸出:

檢測陽性的比例           = 0.01122
陽性中真正患病的比例     = 0.08981
貝氏定理理論值           = 0.09016

陽性比例約 1.1%(理論 0.01098),陽性群體中真正的患者只有 8.98%,與貝氏定理的 9.02% 吻合到 \(1/\sqrt{N} \approx 0.001\) 的量級——百萬人實驗重現了悖論。

模擬的做法就是上表的程式版:先給每人擲一次「是否患病」(機率 1/1000),再按身分擲「是否陽性」(患者過門檻 sens、健康者過門檻 1-spec)。最後在陽性子群體裡數患者的比例——又見 2.3 節的條件機率模擬法。模擬與理論的偏差在 \(1/\sqrt{N} \approx 0.001\) 量級內。


與 R 對照#

set.seed(42)
N <- 1000000
sick <- runif(N) < 1/1000
test_pos <- ifelse(sick, runif(N) < 0.99, runif(N) < 0.01)
mean(test_pos)                              # 陽性比例
mean(sick[test_pos])                        # 陽性中真正患病
(0.99 * 0.001) / (0.99 * 0.001 + 0.01 * 0.999)  # 貝氏理論值

輸出:

[1] 0.011076
[1] 0.09100758
[1] 0.09016393

mean(sick[test_pos]) 這行就是貝氏定理:在陽性子集合裡求患病的平均——條件機率的向量化寫法。


小結#

  1. 互斥是「不能同時發生」(強依賴),獨立是「互不提供資訊」( \(P(AB) = P(A)P(B)\) );正機率下兩者不可兼得。
  2. Bayes(1763 遺稿,Price 整理;Laplace 推廣)解決了逆機率問題: \(P(A \mid B) = \dfrac{P(B \mid A) P(A)}{P(B)}\) 。
  3. 先驗 × 概似 → 後驗:貝氏定理是資訊更新、也是所有機器學習「從數據學規律」的數學原型。
  4. 疾病篩檢悖論(靈敏度 99%、盛行率 1/1000 → 陽性後真患病僅約 9%)的教訓:方向不能顛倒、基率不能忽略;自然頻率(100 萬人排表)是最強的解毒劑。

練習#

  1. 兩事件 \(P(A) = 0.4\) 、 \(P(B) = 0.5\) 。若 \(A\) 、 \(B\) 互斥, \(P(A \cup B)\) 是多少?若獨立呢?並判斷這兩種情形下 \(P(A \mid B)\) 各為何。(提示:互斥給 0,獨立給 0.4。)
  2. 把篩檢問題的盛行率改成 1/100(高危群體),重算 \(P(D \mid +)\) ;再用程式把盛行率從 0.001 掃到 0.1,畫出(或列表)後驗的變化。(提示:理論約 0.5005;後驗隨基率單調上升。)
  3. 複檢問題:某人第一次篩檢陽性(後驗 9.02%)。若複檢與初檢條件獨立且同為 99%/99% 的檢查,複檢又陽性,此時患病機率多少?(提示:先驗換成 0.0902, \(\frac{0.99 \times 0.0902}{0.99 \times 0.0902 + 0.01 \times 0.9098} \approx 0.907\) 。)
  4. 蒙提霍爾問題用貝氏定理證明「換門獲勝機率 2/3」,並模擬 10 萬次驗證兩種策略。(提示:先驗 \(P(\text{車在2}) = 1/3\) ;觀察到「主持人開 3」的概似:車在 2 時為 1,車在 1 時為 1/2。)
  5. 某測謊器說謊偵測率 95%、誠實誤判率 10%。若一群人中有 5% 說謊,被測出「說謊」的人真說謊的比例是多少?用自然頻率(10 萬人)列表並程式驗證。(提示:約 33%。)