最尤推定で「最も尤もらしい」分布パラメータを見つける
データセットを与え、尤度関数を最大にする平均と分散を探索し、np.mean / np.std の結果と一致するか比較する。
このケースを学ぶと、次のことが理解できます:「データが出現する確率を最大にする」パラメータは、まさに標本平均と標本標準偏差である。
生活からの導入
魚塘の魚の平均重量を推測する
あなたは魚塘のすべての魚の平均重量を知らない。しかし、200匹の魚をすくって重量を量った。自然とこう考えるだろう:どのような「平均重量」ならば「ちょうどこの200匹の魚のこれらの重量を量る」という出来事が最も起こり得るだろうか?
直感は、200匹の魚の平均重量が良い推定であることを教えてくれる。最尤推定(MLE)はこの直感を数学的にしたものである:このデータセットが観測される確率を最大にするパラメータ値を見つける。
数学的定義
ガウス分布の対数尤度
\[ \log L(\mu, \sigma) = -\frac{n}{2}\log(2\pi\sigma^2) - \frac{1}{2\sigma^2}\sum_{i=1}^{n}(x_i - \mu)^2 \]MLEの解析解
\[ \hat{\mu}_{\text{MLE}} = \frac{1}{n}\sum_{i=1}^{n} x_i = \bar{x}, \quad \hat{\sigma}_{\text{MLE}} = \sqrt{\frac{1}{n}\sum (x_i - \bar{x})^2} \]これは偶然ではない。ガウス分布のMLE解析解は、まさに標本平均と標本標準偏差である。
Pythonで実践
実例
import numpy as np
np.random.seed(3)
true_mu, true_sigma = 5.0, 2.0
data = np.random.normal(true_mu, true_sigma, size=200)
# ガウス対数尤度関数
def log_likelihood(mu, sigma, data):
n = len(data)
return (-n/2) * np.log(2 * np.pi * sigma**2) \
- np.sum((data - mu)**2) / (2 * sigma**2)
# 総当たりグリッドサーチでMLEを求める
mu_grid = np.linspace(3, 7, 100)
sigma_grid = np.linspace(0.5, 4, 100)
best_ll = -np.inf
best_mu, best_sigma = None, None
for mu in mu_grid:
for sigma in sigma_grid:
ll = log_likelihood(mu, sigma, data)
if ll > best_ll:
best_ll = ll
best_mu, best_sigma = mu, sigma
print("=" * 55)
print("サンプル 最尤推定 (MLE) の結果")
print("=" * 55)
print(f"グリッドサーチ MLE: mu={best_mu:.4f}, sigma={best_sigma:.4f}")
print(f"公式で直接計算: mu={data.mean():.4f}, sigma={data.std():.4f}")
print(f"実際の生成パラメータ: mu={true_mu}, sigma={true_sigma}")
print(f"\n結論: MLE = np.mean/np.std —— 偶然ではなく、数学の定理である")
np.random.seed(3)
true_mu, true_sigma = 5.0, 2.0
data = np.random.normal(true_mu, true_sigma, size=200)
# ガウス対数尤度関数
def log_likelihood(mu, sigma, data):
n = len(data)
return (-n/2) * np.log(2 * np.pi * sigma**2) \
- np.sum((data - mu)**2) / (2 * sigma**2)
# 総当たりグリッドサーチでMLEを求める
mu_grid = np.linspace(3, 7, 100)
sigma_grid = np.linspace(0.5, 4, 100)
best_ll = -np.inf
best_mu, best_sigma = None, None
for mu in mu_grid:
for sigma in sigma_grid:
ll = log_likelihood(mu, sigma, data)
if ll > best_ll:
best_ll = ll
best_mu, best_sigma = mu, sigma
print("=" * 55)
print("サンプル 最尤推定 (MLE) の結果")
print("=" * 55)
print(f"グリッドサーチ MLE: mu={best_mu:.4f}, sigma={best_sigma:.4f}")
print(f"公式で直接計算: mu={data.mean():.4f}, sigma={data.std():.4f}")
print(f"実際の生成パラメータ: mu={true_mu}, sigma={true_sigma}")
print(f"\n結論: MLE = np.mean/np.std —— 偶然ではなく、数学の定理である")
======================================================= サンプル 最大似然估计 (MLE) 结果 ======================================================= 网格搜索 MLE: mu=4.9394, sigma=2.0480 公式直接算: mu=4.9394, sigma=2.0480 真实生成参数: mu=5.0, sigma=2.0 结论: MLE = np.mean/np.std —— 不是巧合,是数学定理
AIにおける応用シーン
| 場面 | MLEとの関連 |
|---|---|
| クロスエントロピー損失 | 分類タスクでクロスエントロピーを最小化する = カテゴリ分布に対するMLE |
| MSE損失 | 回帰タスクでMSEを最小化する = 誤差がガウス分布に従うと仮定したMLE |
| パラメータ初期化 | データの統計量でモデルパラメータを初期化する——本質はMLEの直感である |