<jupyter_start><jupyter_text>機率分配我們可以將機率分配想成：描述各個**隨機變數**的值發生機率的函數。以`連續投擲兩次公正銅板的正面次數`這個隨機變數 $X$ 為例:- 樣本空間為 $\mathcal{S} = \{(T, T), (T, H), (H, T), (H, H)\}$- 隨機變數為函數 $X: \mathcal{S} \rightarrow \mathbb{R}$ ，我們將樣本空間 $\mathcal{S}$ 的**事件**映射到**實數**上，變成 $\{0, 1, 1, 2\}$- 樣本空間 $\mathcal{S}$ 的樣本點發生機率都相同 (因為每次丟銅板出現正面或反面的機率都是相同的，舉例來說: `連續兩次反面`的機率會等於`第一次正面，第二次反面`的機率。)- 我們可以看作:$$\begin{cases}\frac{1}{4} & E = (T, T) \\\frac{1}{4} & E = (T, H) \\\frac{1}{4} & E = (H, T) \\\frac{1}{4} & E = (H, H)\end{cases}\underset{\implies}{映射}\begin{cases}\frac{1}{4} & X = 0 \\\frac{1}{4} & X = 1 \\\frac{1}{4} & X = 1 \\\frac{1}{4} & X = 2\end{cases}\underset{\implies}{合併}\begin{cases}\frac{1}{4} & X = 0 \\\frac{1}{2} & X = 1 \\\frac{1}{4} & X = 2\end{cases}$$- 最後得到的式子，就是隨機變數 $X$ 的機率分配，在**離散隨機變數**的情況下，又可以稱作**機率質量函數**。附上用程式碼畫出分佈的範例<jupyter_code>from typing import Tuple
from itertools import groupby

import plotly.graph_objects as go

# 樣本空間
S = {('T', 'T'), ('T', 'H'), ('H', 'T'), ('H', 'H')}

# 隨機變數
def X(event: Tuple[str, str]) -> int:
    '''隨機變數 - 連續投擲兩次公正硬幣，正面的次數

    Args:
        event (Tuple[str, str]): 連續投擲兩次公正銅板的事件

    Returns:
        head (int): 正面的次數
    '''
    head = 0

    for trial in event:
        if trial == 'H':
            head += 1

    return head

# 將樣本空間映射
S_new = sorted([X(event) for event in S])

# 製作機率分配
distribution = []

for x, outcomes in groupby(S_new):
    distribution.append({
        'x': x,
        'prob': len([out for out in outcomes]) / len(S_new)
    })

# 畫圖
bar = go.Bar(
    x=[pt['x'] for pt in distribution],
    y=[pt['prob'] for pt in distribution],
)
fig = go.Figure(data=[bar])
fig.update_layout(
    title="連續投擲兩次公正銅板出現正面次數的機率分配",
    xaxis_title="正面的次數",
    yaxis_title="機率",
)
fig<jupyter_output><empty_output><jupyter_text>離散型機率分配```{admonition} 機率質量函數 (probability mass function)給定離散型隨機變數 $X$ ，若函數 $f_X(x)$ 滿足- $0 \leq f_X(x) \leq 1, \forall x \in \mathbb{R}$- $\sum_{x \in \mathbb{R}} f_X(x) = 1$- $f_X(x \in A) = \sum_{x \in A} f_X(x)$我們稱其為隨機變數 $X$ 的機率質量函數。```- 機率質量函數的值**就是**機率。  伯努利分配 (Bernoulli Distribution)```{admonition} 定義假設隨機變數 $X$ 為**一次**隨機試驗成功的次數，其樣本空間 $\mathcal{S} = \{ Success, Failure \}$ ，而機率質量函數 $f_X(x)$ 為$$f_X(x) = \begin{cases}1 - p & x = 0 \\p & x = 1 \\0 & otherwise\end{cases}$$$0 \leq p \leq 1$ ，成功機率為 $p$ ，失敗機率為 $1 - p$ 。我們記作$$X \sim \mathcal{Ber}(p)$$```- Bernoulli 分配就是 $n = 1$ 的 Binomial 分配假設有一個不公正硬幣，其正面的機率為 $p = 0.7$ ，隨機變數 $X$ 為投擲**一次**這個硬幣出現正面的次數，所以其機率質量函數 $f_X(x)$ 可以寫成$$f_X(x) = \begin{cases}0.7 & x = 1 \\0.3 & x = 0 \\0 & otherwise\end{cases}$$下面程式碼是畫出 $p = 0.7$ 伯努利分配的機率質量函數。<jupyter_code>import plotly.graph_objects as go

# 隨機變數
X = {0, 1}

# 機率質量函數
f = {0: 0.3, 1: 0.7}

# 畫出機率質量函數
bar = go.Bar(x=list(X), y=[f[x] for x in X])
fig = go.Figure(data=[bar],
                layout=go.Layout(
                    title={'text': 'Bernoulli Distribution (p = 0.7)'},
                    xaxis={'title': '$x$'},
                    yaxis={'title': '$f(x)$'}))
fig<jupyter_output><empty_output><jupyter_text>二項分配 (Binomial Distribution)```{admonition} 定義假設隨機變數 $X$ 為 **n次**隨機試驗成功的次數，其樣本空間 $\mathcal{S} = \{(Success, Success, ...), ..., (Failure, Failure, ...)\}$ ，機率質量函數 $f_X(x)$ 為$$f_X(x) = \begin{cases}\binom{n}{x}p^x(1-p)^{(n-x)} & x = 0, 1, ..., n \\0 & otherwise\end{cases}$$我們記作$$X \sim \mathcal{Binom}(n, p)$$```- 二項分配就是執行**n次**的伯努利分配給定隨機變數 $X$ 為`投擲10次公正硬幣出現正面的次數`，其中出現正面的機率 $p = 0.5$ ，機率質量函數可以寫成$$f_X(x) = \begin{cases}\binom{10}{x} \cdot 0.5^{x} \cdot (1 - 0.5)^{10 - x} & x = 0, 1, ..., 10 \\0 & otherwise\end{cases}$$下面提供畫出隨機變數 $X$ 機率質量函數的程式碼<jupyter_code>from typing import Tuple
from itertools import product
from collections import Counter

import plotly.graph_objects as go

# 樣本空間
S = {out for out in product([0, 1], repeat=10)}

# 隨機變數


def X(event: Tuple) -> int:
    '''隨機變數 - 連續投擲10次公正硬幣出現正面的次數

    Args:
        event (Tuple): 連續投擲10次公正硬幣的結果

    Returns:
        head (int): 出現正面的次數
    '''
    return sum(event)


# 將樣本空間映射
S_new = [X(event) for event in S]

# 機率分配
distribution = Counter(S_new)

# 畫圖
data = [
    go.Bar(
        x=[x for x in range(0, 11)],
        y=[
            distribution[count] / sum(distribution.values())
            for count in range(0, 11)
        ],
    )
]
fig = go.Figure(data=data,
                layout=go.Layout(
                    title={'text': 'Binomial Distribution (n=10, p=0.5)'},
                    xaxis={'title': '$x$'},
                    yaxis={'title': '$f(x)$'}))
fig<jupyter_output><empty_output><jupyter_text>二項分配近似常態分配二項分配在 $n$ 夠大的時候會近似常態分配。假設有隨機變數 $X_n \sim \mathcal{Binom}(n, p), \forall n \in \mathbb{Z}$ ，在 $n$ 夠大時會趨近於常態分配$$\lim_{n \rightarrow \infty} X_n \overset{\text{approx.}}{\sim} \mathcal{N}(\mu = np, \sigma^2 = np(1 - p))$$期望值 $\mu = np$ ，變異數 $\sigma^2 = np(1-p)$ 。<jupyter_code>import numpy as np
from scipy.stats import binom, norm
from plotly.subplots import make_subplots
import plotly.graph_objects as go

ns = [10, 30, 100]
p = 0.5

fig = make_subplots(rows=3, cols=1, subplot_titles=[f'$n = {n}$' for n in ns])

for i, n in enumerate(ns, start=1):
    # 畫出二項分配 pmf
    fig.add_trace(
        go.Bar(x=[x for x in range(n + 1)],
               y=[binom.pmf(x, n, p) for x in range(n + 1)],
               name=f'$\mathcal{{B}}(n = {n}, p={p})$'),
        row=i,
        col=1,
    )

    # 畫出常態分配 N(np, np(1-p)) 的 pdf
    mean = n * p
    var = n * p * (1 - p)
    std_error = np.sqrt(var)
    points = np.linspace(mean - 3 * std_error, mean + 3 * std_error, 1000)

    label = r'$\mathcal{{N}}(\mu = {mu}, \sigma = \sqrt{{{var}}})$'.format(
        mu=mean, var=var)
    fig.add_trace(
        go.Scatter(x=points,
                   y=[norm.pdf(x, mean, std_error) for x in points],
                   mode='lines',
                   name=label),
        row=i,
        col=1,
    )

fig.update_layout(title={'text': '二項分配近似常態分配'})
fig<jupyter_output><empty_output><jupyter_text>連續型機率分配```{admonition} 機率密度函數 (probability density function)給定連續型隨機變數 $X$ ，若函數 $f_X(x)$ 滿足- $f_X(x) \geq 0$- $\int_{\mathbb{R}}f_X(x)dx = 1$- $\mathbb{P}(X \in A) = \int_{A} f_X(x) dx, A \subset \mathbb{R}$我們稱其為隨機變數 $X$ 的機率密度函數。```- 機率密度函數的值**不是**機率，機率需要對特定區域**積分**獲得。假設有一個隨機變數 $X$ 在0到100間出現的機率都相等，其機率密度函數可以寫成$$f_X(x) = \begin{cases}\frac{1}{100 - 0} & 0 \leq x \leq 100 \\0 & otherwise\end{cases}$$因為連續型的隨機變數，其機率需要靠**積分**得到，所以單點機率 $\mathbb{P}(X = x) = \int_{x}^x f_X(x)dx = 0$ 。但若給定範圍，例如 $\mathbb{P}(0 \leq X \leq 50) = \int_{0}^{50} f_X(x)dx = \int_{0}^{50} \frac{1}{100}dx = \frac{x}{100}\big|_{0}^{50} = 0.5$ 。此分配又稱為**均勻分配**。下面的程式碼示範將這個隨機變數的機率密度函數畫出來<jupyter_code>import plotly.graph_objects as go
import numpy as np

# 上界與下界
a, b = 0, 100

# 機率密度函數


def f(a, b, x):
    if x >= a and x <= b:
        return 1 / (b - a)
    else:
        return 0


# 製作機率密度函數的點
xs = np.linspace(a - 10, b + 10, 1000)
ys = [f(a, b, x) for x in xs]

# 製作0到50機率面積的點
prob_xs = np.linspace(0, 50, 1000)
prob_ys = [f(a, b, x) for x in prob_xs]

# 畫出機率密度函數與0到50的機率
data = [
    go.Scatter(x=xs, y=ys, mode='lines', name='機率密度函數'),
    go.Scatter(x=prob_xs,
               y=prob_ys,
               mode='lines',
               fill='tozeroy',
               name='0到50的機率值')
]
fig = go.Figure(data,
                layout=go.Layout(title={'text': '連續型機率分配'},
                                 xaxis={'title': '$x$'},
                                 yaxis={'title': '$f(x)$'}))
fig<jupyter_output><empty_output>
{'fraction_non_alphanumeric': 0.20983294852641587, 'fraction_numerical': 0.027570283851690885, 'mean_word_length': 2.9956592512208355, 'pattern_counts': {'":': 0, '<': 22, '<?xml version=': 0, '>': 24, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 3, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'chain_length': '5', 'dir': 'jupyter-structured-clean-dedup', 'id': '470552', 'license': 'MIT', 'n_tokens_mistral': 4080, 'n_tokens_neox': 4131, 'n_words': 678, 'path': 'doc/probability/distribution.ipynb', 'repo_name': 'r05323028/primer-on-statistics', 'size': '7363'}