Networks/Hands-On 머신러닝 정리

Hands-On Machine Learning 정리 - 머신러닝(Chapter 9: 비지도 학습) - Part. 2

코딩하는 Español되기 2024. 10. 22. 18:00

Chpa 9 비지도 학습 부분에서 군집 부분과 가우시안 혼합 부분의 양이 많아서 Part-1과 Part-2로 각각 나누어 포스팅했습니다. 이번 글에서는 가우시안 혼합에 관하여 알아보겠습니다.


Part-1 바로 가기(Chap9- 군집)

Chap9 목차

1. 군집

    - k-평균

    - 군집을 사용한 이미지 분할, 전처리, 준지도 학습

    - DBSCAN

    - 다른 군집 알고리즘

2. 가우시안 혼합

   - 이상치 탐지

   - 클러스터 개수 선택(가능도 함수)

   - 베이즈 가우시안 혼합 모델

   - 이상치/특이치 탐지를 위한 알고리즘


2. 가우시안 혼합(GMM;Gaussian Mixture Model)

○ 샘플이 파라미터가 알려지지 않은 여러 개의 혼합된 가우시안 분포에서 생성되었다고 가정하는 확률 모델

○ 하나의 가우시안 분포에서 생성된 모든 샘플은 하나의 클러스터를 형성(일반적으로 클러스터는 타원형)

    ● 각 클러스터는 아래 그림처럼 타원의 모양, 크기, 밀집도, 방향이 diff

    ● 샘플이 주어지면 가우시안 분포 중 하나에서 생성되었다는 것을 알 수 있음

    ● But 어떤 분포인지, 이 분포의 파라미터는 무엇인지 알지 못함

○ 여러 GMM 변종이 존재하지만 가장 간단한 버전은 GaussianMixture 클래스에 구현되어 있음

    ● 사전에 가우시안 분포의 개수 k를 알아야 함

    ● 가정: 데이터셋 X가 아래 확률 과정을 통해 생성되었다

$$ \textup{샘플마다 k개의 클러스터에서 랜덤하게 한 클러스터가 선택됨} $$

$$ \textup{j번째 클러스터를 선택할 확률 = 가중치 \phi^{j}로 정의됨} $$

$$ \textup{i번째 샘플을 위해 선택한 클러스터 인덱스는} z^{(i)} \textup{로 표시} $$

$$ z^{(i)}=j \textup{이면, 즉 i번째 샘플이 j번째 클러스터에 할당되었다면} $$

$$ \textup{이 샘플의 위치} x^{(i)} \textup{는 평균이} \mu^{(j)} \textup{이고} $$

$$ \textup{공분산 행렬이} \sum^{(j)} \textup{인 가우시안 분포에서 랜덤하게 샘플링됨} $$

$$ \textup{이를} x^{(i)}\sim N(\mu^{(i)},\sum^{(j)}) \textup{와 같이 씁니다.} $$

○ 위의 생성 과정은 그래프 모형으로 나타낼 수 있음

    ● 아래 그림은 확률 변수 사이의 조건부 의존성(Conditional Dependency)의 구조를 나타냄

 

플레이트 표기법

    ● 원: 확률 변수

    ● 사각형: 고정값(모델 파라미터)

    ● 큰 사각형(플레이트): 해당 사각형 안의 내용이 여러 번 반복됨

    ● 각 플레이트의 오른쪽 아래숫자(m, k): 플레이트 안의 내용 반복 횟수

    ● 각 변수 z^{(i)}는 가중치 \phi를 갖는 범주형 분포에서 샘플링.

    ● 각 변수 x^{(i)}는 해당하는 클러스터 z^{(i)}로 정의된 평균과 공분산 행렬을 사용해 정규분포에서 샘플링

    ● 실선 화살표: 조건부 의존성 표현

        - 각 확률 변수 z^{(i)}의 확률 분포는 가중치 벡터 \phi에 의존

        - 화살표가 플레이트 경계를 가로지르면 해당 플레이트의 모든 반복에 적용한다는 의미

        e.g. 가중치 벡터 \phi는 확률 변수 x^{(1)} ~ x^{(m)}까지 모든 확률 변수의 확률 분포에 필요 조건

    ● 구불구분한 화살표: 스위치. z^{(i)}의 값에 따라 샘플 x^{(i)}가 다른 가우시안 분포에서 샘플링된 것

        e.g.

$$ \textup{if} z^{(i)}=j ... x^{(i)} \sim N(\mu^{(j)}, \sum^{(j)}) $$

    ● 색이 채워진 원: 알려진 값(이 경우 확률 변수 x^{(i)} ← 관측 변수)

     ※ 알려지지 않은 변수: 잠재 변수(이 경우 확률 변수 z^{(i)})

○ 모델 활용

    ● 데이터셋 x가 주어지면 가중치 Φ와 전체 파라미터 mu^{(1)} ~ mu^{(k)}까지와 ∑^{(1)} ~ ∑^{(k)}까지 추정

    ● 사이킷런의 GaussianMixture 클래스 사용

    ● 가우시안 모델 = 생성 모델 (즉, 모델에서 새로운 샘플을 만들 수 있음)

    ※ 반환된 샘플은 클러스터 인덱스 순으로 정렬되어 있음

    ● 주어진 위치에서 모델의 밀도를 추정 가능(score_samples() 메서드 사용)

        - 샘플이 주어지면 이 메서드는 그 위치의 확률 밀도 함수(PDF)의 로그를 예측(점수가 높을 수록 밀도가 높음)

        - 이 점수의 지숫값을 계산하면 샘플 위치에서 PDF 값을 얻을 수 있음(하나의 확률 X, 확률 밀도)

          So, 범위가 0 ~ 1이 아니라 어떤 양숫값도 될 수 있음

    ● 샘플이 특정 지역 안에 속할 확률을 예측하려면 그 지역에 대해 PDF를 적분해야함

    ● 아래 그림은 모델의 클러스터 평균, 결정 경계(파선), 밀도 등고선을 보여줌

○ 코드

    ● 실제 데이터를 생성하기 위해 사용한 가중치, 평균, 분산 행렬도 이 알고리즘이 찾은 것과 매우 비슷

    ● GaussianMixture 클래스는 기댓값-최대화(EM;Expectation-Maximization)알고리즘을 사용

 

○ EM 알고리즘

    ● k-평균 알고리즘과 공통점

        - 클러스터 파라미터를 랜덤하게 초기화하고 수렴할때까지 두 단계를 반복

        - But, k-평균과 달리 EM은 하드 클러스터 할당이 아니라 소프트 클러스터 할당을 사용

        e.g. 기댓값 단계에서 알고리즘은 각 클러스터에 속할 확률을 예측

               → 최대화 단계에서 각 클러스터가 데이터셋에 있는 모든 샘플을 사용해 업데이트

       ※ 기댓값 단계에서 확률 = 샘플에 대한 클러스터의 책임 

       ※ 최대화 단계에서 클러스터 업데이트는 책임이 가장 많은 샘플에 크게 영향을 받음

    ● 단계

        - 샘플을 클러스터에 할당(기댓값 단계)

        - 클러스터 업데이트(최대화 단계)

    ● 특성이나 크러스터가 많거나 샘플이 적을 때는 EM이 최적의 솔루션으로 수렴하기 어려움

        - 알고리즘이 학습할 파라미터 개수를 제한해야 함

 

공분산 행렬에 제약을 추가하는 방법(사이킷런에 covariance_type 매개변수에 다음 값 중 하나를 설정)

    ● "full"(기본값): 각 클러스터는 모양, 크기, 방향에 제약이 없음(제약 없는 공분산 행렬을 가짐)

    ● "spherical": 모든 클러스터가 원형으로 지름(= 분산)이 다를 수 있음

    ● "diag": 클러스터는 크기에 상관없이 어떤 타원형도 가능 But 타원의 축은 좌표 축과 나란해야함

                   (= 즉, 공분산 행렬이 대각 행렬이어야 함)

    ● "tied": 모든 클러스터가 동일한 타원 모양, 크기, 방향을 가짐

                  (= 즉, 모든 클러스터는 동일한 공분산 행렬을 공유)

GaussianMixture모델을 훈련하는 계산복잡도
○ 샘플 개수 m, 차원 개수 n, 클러스터 개수 k와 공분산 행렬에 있는 제약에 따라 결정
○ covariance_type이 "spherical"이나 "diag"면 데이터에 어떤 클러스터 구조가 있다고 가정하면
    ● O(kmn)
○ convariance_type이 "tied"나 "full"이면 O(kmn^{2}+kn^{3}) So, 특성 개수가 많으면 적용이 어려움

[코드]

더보기

- 데이터셋

X1, y1 = make_blobs(n_samples=1000, centers=((4, -4), (0, 0)), random_state=42)
X1 = X1.dot(np.array([[0.374, 0.95], [0.732, 0.598]]))
X2, y2 = make_blobs(n_samples=250, centers=1, random_state=42)
X2 = X2 + [6, -8]
X = np.r_[X1, X2]
y = np.r_[y1, y2]

 

- GaussianMixture 클래스 사용하여 훈련

from sklearn.mixture import GaussianMixture

gm = GaussianMixture(n_components=3, n_init=10, random_state=42)
gm.fit(X)

 

- 알고리즘이 추정한 파라미터 확인

※ 특성이 두 개이므로 평균이 특성마다 하나씩 반환 & 공분산 행렬의 크기 = 2*2

gm.weights_ # array([0.39025715, 0.40007391, 0.20966893])

gm.means_
# array([[ 0.05131611,  0.07521837],
#       [-1.40763156,  1.42708225],
#       [ 3.39893794,  1.05928897]])

gm.covariances_
#array([[[ 0.68799922,  0.79606357],
#        [ 0.79606357,  1.21236106]],

#       [[ 0.63479409,  0.72970799],
#        [ 0.72970799,  1.1610351 ]],

#       [[ 1.14833585, -0.03256179],
#        [-0.03256179,  0.95490931]]])

# 수렴 여부 확인
gm.converged_ # True

# 반복 횟수 확인
gm.n_iter_ # 4

 

- 각 클러스터의 위치, 크기, 모양, 방향, 상대적인 가중치 예측

    ● 이 모델은 새로운 샘플을 가장 비슷한 클러스터에 손쉽게 할당 가능(하드 군집) → predict() 메서드 사용

    ● 특정 클러스터에 속활 확률을 예측하는 것도 가능(소프트 군집) → predict_proba() 메서드 사용

# 하드 군집
gm.predict(X)

# 소프트 군집
gm.predict_proba(X)

 

- 생성된 모델에서 새로운 샘플 생성

X_new, y_new = gm.sample(6)
X_new
y_new

 

- 밀도 추정 (PDF 로그 예측)

gm.score_samples(X)

 

- 시각화 코드

from matplotlib.colors import LogNorm

def plot_gaussian_mixture(clusterer, X, resolution=1000, show_ylabels=True):
    mins = X.min(axis=0) - 0.1
    maxs = X.max(axis=0) + 0.1
    xx, yy = np.meshgrid(np.linspace(mins[0], maxs[0], resolution),
                         np.linspace(mins[1], maxs[1], resolution))
    Z = -clusterer.score_samples(np.c_[xx.ravel(), yy.ravel()])
    Z = Z.reshape(xx.shape)

    plt.contourf(xx, yy, Z,
                 norm=LogNorm(vmin=1.0, vmax=30.0),
                 levels=np.logspace(0, 2, 12))
    plt.contour(xx, yy, Z,
                norm=LogNorm(vmin=1.0, vmax=30.0),
                levels=np.logspace(0, 2, 12),
                linewidths=1, colors='k')

    Z = clusterer.predict(np.c_[xx.ravel(), yy.ravel()])
    Z = Z.reshape(xx.shape)
    plt.contour(xx, yy, Z,
                linewidths=2, colors='r', linestyles='dashed')
    
    plt.plot(X[:, 0], X[:, 1], 'k.', markersize=2)
    plot_centroids(clusterer.means_, clusterer.weights_)

    plt.xlabel("$x_1$", fontsize=14)
    if show_ylabels:
        plt.ylabel("$x_2$", fontsize=14, rotation=0)
    else:
        plt.tick_params(labelleft=False)
plt.figure(figsize=(8, 4))

plot_gaussian_mixture(gm, X)

plt.show()

2-1 가우시안 혼합을 사용한 이상치 탐지

이상치 탐지(Outlier Detection): 보통과 많이 다른 샘플을 감지하는 작업

   사용 e.g. 부정 거래 감지, 제조 결함이 있는 제품 감지, 다른 모델 훈련하기 전 데이터셋에서 이상치 제거에 사용

○ 사용법

    ● 밀도가 낮은 지역에 있는 모든 샘플을 이상치로 볼 수 있음 → 사용할 밀도 임곗값을 정해야 함

    ● IF 거짓 양성이 너무 많다면(정상인 제품이 결함으로 표시) → 임곗값 낮추기

       Else 거짓 음성이 너무 많다(결함 제품이 결함으로 표시 X) → 임곗값 높이기

    ※ 일반적인 정밀도/재현율 트레이드 오프

○ 네 번째 백분위수(4%)를 밀도 임곗값으로 사용해 이상치를 구분하는 방법

    ● 이와 같은 작업이 특이치 탐지(Novelty Detection)

    ● 이상치로 오염되지 않은 깨끗한 데이터셋에서 훈련한다는 것이 이상치 탐지와의 차이

○ 가우시안 혼합 모델은 이상치를 포함해 모든 데이터에 맞추려고 함
○ 이상치가 너무 많으면 모델이 정상치를 바라보는 시각이 편향되고 일부 이상치를 정상으로 잘못 생각 가능
○ IF 이런 일이 발생 → 한 모델 훈련 하고 가장 크게 벗어난 이상치 제거 → 정제된 데이터셋에서 모델 다시 훈련
○ 다른 방법: 안정적인 공분산 추정 방법 사용

[코드]

더보기
densities = gm.score_samples(X)
density_threshold = np.percentile(densities, 4)
anomalies = X[densities < density_threshold]

- 시각화

plt.figure(figsize=(8, 4))

plot_gaussian_mixture(gm, X)
plt.scatter(anomalies[:, 0], anomalies[:, 1], color='r', marker='*')
plt.ylim(top=5.1)

plt.show()

2-2 클러스터 개수 선택하기(가능도 함수)

○ k-평균에서는 이너셔나 실루엣 점수를 사용해 적절한 클러스터 개수를 선택 But, 가우시안 혼합에서는 사용 불가

∵ 이런 지표들은 클러스터가 타원형 | 크기가 다를 때 안정적이지 않기 때문

○ 대신 BIC(Bayesian Information Criterion)나 AIC(Akaike Information Criterion) 사용

    ● 이론적 정보 기준을 최소화하는 모델을 찾음

○ BIC와 AIC

    ● 학습할 파라미터가 많은(클러스터가 많은)모델에게 벌칙을 가하고 데이터에 잘 학습하는 모델에게 보상을 더함

    ● IF 둘의 선택이 다름 → BIC가 선택한 모델이 AIC가 선택한 모델보다 간단한(파라미터가 적은) 경향이 있음

       But, 데이터에 아주 잘 맞지 않을 수 있음(특히 대규모 데이터셋에서)

[BIC와 AIC공식]

$$ BIC = log(m)p - 2log(\hat{L}) $$

$$ AIC = 2p - 2log(\hat{L}) $$

    ● m: 샘플 개수

    ● p: 모델이 학습할 파라미터 개수

    ● \hat{L}: 모델의 가능도 함수(Likelihood function)의 최댓값

[BIC와 AIC 코드]

    ● bic()와 aic() 메서드 사용

    ● 여러가지 클러스터 개수 k에 대한 AIC와 BIC를 보여줌(k=3에서 BIC와 AIC가 가장 작음 So, k=3이 최선)

    ● covariance_type 매개변수에 대해 최선의 값 탐색도 가능

더보기
gm.bic(X) # 8189.747000497186
gm.aic(X) # 8102.521720382148

 

- BIC 수동 계산

n_clusters = 3
n_dims = 2
n_params_for_weights = n_clusters - 1
n_params_for_means = n_clusters * n_dims
n_params_for_covariance = n_clusters * n_dims * (n_dims + 1) // 2
n_params = n_params_for_weights + n_params_for_means + n_params_for_covariance
max_log_likelihood = gm.score(X) * len(X) # log(L^)
bic = np.log(len(X)) * n_params - 2 * max_log_likelihood
aic = 2 * n_params - 2 * max_log_likelihood
bic, aic # (8189.747000497186, 8102.521720382148)
n_params # 17

 

- 시각화 코드

gms_per_k = [GaussianMixture(n_components=k, n_init=10, random_state=42).fit(X)
             for k in range(1, 11)]
bics = [model.bic(X) for model in gms_per_k]
aics = [model.aic(X) for model in gms_per_k]
plt.figure(figsize=(8, 3))
plt.plot(range(1, 11), bics, "bo-", label="BIC")
plt.plot(range(1, 11), aics, "go--", label="AIC")
plt.xlabel("$k$", fontsize=14)
plt.ylabel("Information Criterion", fontsize=14)
plt.axis([1, 9.5, np.min(aics) - 50, np.max(aics) + 50])
plt.annotate('Minimum',
             xy=(3, bics[2]),
             xytext=(0.35, 0.6),
             textcoords='figure fraction',
             fontsize=14,
             arrowprops=dict(facecolor='black', shrink=0.1)
            )
plt.legend()
plt.show()

 

2-2-1 가능도 함수

    ● 확률과 가능도는 종종 구별없이 사용됨 But 통계학에서는 이 둘은 다른 의미를 가짐

    ● 파라미터가 θ인 확률 모델이 주어지면

         - 확률: 미래 출력 x가 얼마나 그럴 듯한지 설명(파라미터 θ값을 알고 있다면)

         - 가능도: x를 알고 있을 때 특정 파라미터 값 θ가 얼마나 그럴듯한지 설명

    ● e.g. -4와 +1이 중심인 두 개의 가우시안 분포를 가진 1D 혼합 모델

        - 간단히 나타내기 위해 이 모델은 두 분포의 표준편차를 제어하기 위한 파라미터가 θ 하나를 가짐

        - 아래 그림에서 왼쪽 위 그래프는 x와 θ 의 함수로 전체 모델 f(x; θ)를 보여줌

        - 미래 출력 x의 확률 분포를 예측하려면? θ(모델 파라미터)를 지정해야 함

          If θ를 1.3(수평선)으로 지정 → 왼쪽 아래 그래프와 같은 확률 밀도함수 f(x; θ=1.3)을 얻음

       e.g. -2와 +2 사이에 들어갈 확률을 예측하려면 이 범위에서 PDF의 적분을 계산해야 함(그림자 부분의 면적)

    ● 간단히 말해 PDF는 x의 함수(θ 고정), 반면 가능도 함수는 θ의 함수(x 고정)

       ※ 가능도 함수가 확률 분포가 아니라는 것을 이해하는 것이 중요

    ● 가능한 모든 θ에 대해서 가능도 함수를 적분하면 어떤 양숫값도 가능

    ● 데이터셋 X가 주어졌을 때 일반적으로 모델 파라미터에 대해 가장 그럴듯한 값을 예측

       → 이를 위해 X에 대한 가능도 함수를 최대화하는 값을 찾아야 함

    ● 예시의 경우 샘플 x = 2.5 하나를 관측했다면

        -  θ의 최대 가능도 추정(MLE; Maximum Likelihood Estimate)

$$hat{\Theta} = 1.5 $$

        - 최대 사후 확률(MAP; Maximum a-posteriori)

          : θ 에 대한 사전 확률 분포 g가 존재한다면L(θ|x)를 최대화하는 것보다 L{ θ | x )g( θ ) 를 최대화 하는 것이 가능

※ L : Likelihood(가능도)

※ MAP가 파라미터 값을 제약하므로 이를 MLE의 규제 버전으로 생각 가능

    ● 가능도 함수를 최대화하는 것은 이 함수의 로그를 최대화하는 것과 동일(오른쪽 아래 그래프)

        - 로그 함수는 항상 증가하는 함수 So, θ가 로그 가능도를 최대화하면 가능도도 최대화함

 

2-3 베이즈 가우시안 혼합 모델

○ BayesianGaussianMixture 클래스

    ● 최적의 클러스터 개수를 수동으로 찾지 않고 불필요한 클러스터의 가중치를 0으로

    ● 클러스터 개수 n_components를 최적의 클러스터 개수보다 크다고 믿을 만한 값으로 지정

    ● 자동으로 불필요한 클러스터 제거(e.g. 클러스터 개수를 10으로 설정하고 확인)

        - 아래 코드 예시에서는 자동으로 3개의 클러스터가 필요하다는 것을 감지

    ● 이 모델에서 클러스터 파라미터(가중치, 평균, 공분산 행렬 등)은 클러스터 할당처럼 확률 변수로 취급(그림 참고)

       So, 이제 z는 클러스터 파라미터와 클러스터 할당을 모두 포함

더보기
from sklearn.mixture import BayesianGaussianMixture

bgm = BayesianGaussianMixture(n_components=10, n_init=10, random_state=42)
bgm.fit(X)

np.round(bgm.weights_, 2)

 

2-3-1 베타 분포(Beta Distribution)

    ● 고정 범위 안에 놓인 값을 가진 확률 변수를 모델링할 때 자주 사용(범위 0 ~ 1)

    ● e.g. SBP(Stick-Breaking Process)

         - Φ =[0.3, 0.6, 0.5 ...]를 가정하면

         - 샘플의 30%가 클러스터 0에 할당

         - 남은 샘플 60%가 클러스터 1에 할당

         - 그 다음 남은 샘플의 50%가 클러스터 2에 할당

    ● 새로운 샘플이 작은 클러스터보다 큰 클러스터에 합류할 가능성이 높은 데이터셋에 잘 맞는 모델

    ● 농도 α가 크면 Φ 값이 0에 가깝게 되고 SBP는 많은 클러스터를 생성

    ● 농도 α가 작으면 Φ 값이 1에 가깝게 되고 SBP는 몇 개의 클러스터만 생성

    ● 위샤트 분포(Wishart Distribution)을 사용해 공분산 행렬을 샘플링

        - 파라미터 d와 V가 클러스터 분포 모양 제어

    ● 잠재 변수 z에 대한 사전 지식이 사전 확률이라는 확률 분포 p(z)에 인코딩 가능

        - e.g. 클러스터가 적을 것이라는 사전 믿음(낮은 농도)를 가질 수 있음

                 반대로 풍부하다고 믿을 수 있음

        - weight_concentration_prior 매개변수를 사용해 조정 가능 But 데이터가 많을 수록 사전 믿음은 중요하지 않음

※ 사실 이렇게 큰 차이가 나는 그래프를 그리려면 사전 믿음이 매우 강하고 데이터는 작아야 함

[코드]

더보기
bgm_low = BayesianGaussianMixture(n_components=10, max_iter=1000, n_init=1,
                                  weight_concentration_prior=0.01, random_state=42)
bgm_high = BayesianGaussianMixture(n_components=10, max_iter=1000, n_init=1,
                                  weight_concentration_prior=10000, random_state=42)
nn = 73
bgm_low.fit(X[:nn])
bgm_high.fit(X[:nn])
np.round(bgm_low.weights_, 2)
np.round(bgm_high.weights_, 2)
plt.figure(figsize=(9, 4))

plt.subplot(121)
plot_gaussian_mixture(bgm_low, X[:nn])
plt.title("weight_concentration_prior = 0.01", fontsize=14)

plt.subplot(122)
plot_gaussian_mixture(bgm_high, X[:nn], show_ylabels=False)
plt.title("weight_concentration_prior = 10000", fontsize=14)

plt.show()

2-3-2 베이즈 정리

    ● 데이터 X를 관측하고 난 후 잠재 변수에 대한 확률 분포를 업데이트 하는 방법을 설명

    ● X가 주어졌을 때 z의 조건부 확률인 사후 확률 분포 p(z | X)를 계산

$$ p(z|X) = \textup{사후 확률 = } \frac{가능도 * 사전 확률}{증거} = \frac{p(X | z)p(z)}{p(X)} $$

    ● 가우시안 혼합 모델(다른 많은 문제)에서 분모인 p(X)를 계산하기 어려움

       why? 가능한 모든 z값에 대해 적분해야 하기 때문

    ● 모든 클러스터 파라미터와 클러스터 할당의 조합을 고려해야함

$$ p(X)= \int p(X|z)p(z)dz $$

    해결하기 위한 방법

    ● 변분 추론(Variational Inference)

        - 변분 파라미터 λ(람다)를 가진 분포 패밀리 q(z; λ)를 선택

        - q(z)가 p(z|X)의 좋은 근삿값이 되도록 이 파라미터를 최적화

        - q(z)에서 p(z|X)로의 KL(D_KL(q || p) 라고 씀)을 최소화 하는 λ값을 찾아 해결

 

[KL 발산 공식; q(z)에서 p(z|X)로의 KL발산]

    ● 증거의 로그 (log p(X))에서 증거 하한(ELBO;Evidence Lower Bound)를 뺀 식으로 다시 쓸 수 있음

    ● 증거의 로그는 q에 의존하지 않고 상수항이므로 KL 발산을 최소화하려면 ELBO를 최대화해야함

$$ D_{KL}(q \parallel p) = \mathbb{E}_{q}\left [ \textup{log} \frac{q(z)}{p(z|X)}\right ] =$$

$$ \mathbb{E}_{q}\left [ \textup{log} q(z)- \textup{log} p(z|X)\right ] = $$

$$ \mathbb{E}_{q}\left [ \textup{log} q(z)- \textup{log}\frac{p(z, X)}{p(X)}\right ] = $$

$$ \mathbb{E}_{q}\left [ \textup{log} q(z)- \textup{log}p(z, X) + \textup{log}p(X)\right ] =$$

$$ \mathbb{E}_{q}\left [ \textup{log} q(z)\right ]- \mathbb{E}_{q}\left [ \textup{log} p(z, X)\right ] + \mathbb{E}_{q}\left [ \textup{log} p(X)\right ] = $$

$$ \mathbb{E}_{q}\left [ \textup{log} p(X)\right ]- (\mathbb{E}_{q}\left [ \textup{log} p(z, X)\right ] - \mathbb{E}_{q}\left [ \textup{log} q(z)\right ]) = $$

$$ \textup{log}p(X) - \textup{ELBO} $$

$$ \textup{여기서 EBLO =} \mathbb{E}_q[\textup{log}p(z, X)] - \mathbb{E}_q[\textup{log}q(z)] $$

 

실전에서는 다른 기법으로 ELBO를 최대화하는 방법

○ 평균장 변분 추론(Mean Field Variational Inference)

    ● ELBO식을 계산할 수 있는 형태로 단순화하기 위해 분포 패밀리 q(z; λ)와 사전 확률 p(z)를 신중히 선택해야함

    ● 이를 위한 일반적인 방법이 없어 수학적 기술이 필요

    e.g. 사이킷런의 BayesianGaussianMixture클래스에서 사용하는 분포와 하한식은 온라인 문서에 나와 있음 [문서로]

           문서에서 나오는 식에서 클러스터 파라미터와 할당 변수를 위한 업데이트 공식 유도 가능

           그 후 기댓값-최대화 알고리즘에서 매우 비슷하게 사용됨

※ 사실 BayesianGaussianMixture 클래스의 계산복잡도는 GaussianMixture 클래스이 복잡도와 비슷

○ 블랙 박스 확률적 변분 추론(BBSVI;Black Box Stochastic Variational Inference)

    ● 몇 개의 샘플을 q에서 뽑아 변분 파라미터 λ에 대한 ELBO의 그레디언트를 추정하는 데 사용

       그 다음 경사 상승법 스텝에서 사용

    ● 이 방법은(미분 가능하다면) 어떤 종류의 모델과도 베이즈 추론을 사용 가능하게 만들어줌(심지어 심층 신경망도)

    ● 심층 신경망에 사용하는 베이즈 추론을 베이즈 딥러닝이라고함

※ 베이즈 통계학에 관한 자세한 논문(Andrew Gelman 등이 쓴 「Bayesian Data Analysis」(CRC Press, 2014)를 참고

○ 가우시안 혼합 모델은 타원형 클러스터에 잘 작동함

    ● But 다른 모양을 가진 데이터셋에 훈련하면 나쁜 결과를 얻을 수 있음

        e.g. 반달 데이터셋을 군집하기 위해 베이즈 가우시안 혼합 모델 사용(아래 사진)

                - 알고리즘이 2개가 아닌 8개의 클러스터를 찾음

                - 밀도 추정이 너무 나쁘지는 않아서 이상치 감지를 위해 사용 가능

                - But 두 개의 반달 모양을 식별하는 데는 실패

[코드]

더보기
X_moons, y_moons = make_moons(n_samples=1000, noise=0.05, random_state=42)
bgm = BayesianGaussianMixture(n_components=10, n_init=10, random_state=42)
bgm.fit(X_moons)

# 시각화
plt.figure(figsize=(9, 3.2))

plt.subplot(121)
plot_data(X_moons)
plt.xlabel("$x_1$", fontsize=14)
plt.ylabel("$x_2$", fontsize=14, rotation=0)

plt.subplot(122)
plot_gaussian_mixture(bgm, X_moons, show_ylabels=False)

plt.show()

2-4 이상치 탐지와 특이치 탐지를 위한 다른 알고리즘

 

2-4-1 PCA(그리고 inverse_transform() 메서드를 가진 다른 차원 축소 기법)

○ 일반적으로 보통 샘플의 재구성 오차 < 이상치의 재구성 오차

○ So, 간단하고 종종 매우 효과적인 이상치 탐지 기법

 

2-4-2 Fast-MCD(Minimum Covariance Determinant)

EllipticEnvelope 클래스에서 구현된 알고리즘 → 이는 이상치 감지에 유용

○ 특히 데이터셋 정제에 사용

○ 가정

    ● 보통 샘플가 (혼합된 것이 아니라) 하나의 가우시안 분포에서 생성되었다

    ● 이 가우시안 분포에서 생성되지 않은 이상치로 이 데이터셋이 오염되었다

○ 알고리즘이 가우시안 분포의 파라미터를(즉, 정상치를 둘러싼 타원 모형을)추정할 때 이상치로 의심되는 샘플 무시

○ 타원형을 잘 추정하고 이상치를 잘 구분하도록 도움

 

2-4-3 아이솔레이션 포레스트

○ 특히 고차원 데이터셋에서 이상치 감지를 위한 효율적인 알고리즘

○ 무작위로 성장한 결정 트리로 구성된 랜덤 포레스트를 제작

    ● 각 노드에서 특성을 랜덤하게 선택(최솟값과 최댓값 사이)

    ● 랜덤한 임곗값을 선택해 데이터셋을 둘로 나눔

    ● 데이터셋은 점차 분리되어 모든 샘플이 다른 샘플과 격리될 때까지 반복

○ 이상치는 일반적으로 다른 샘플과 멀리 떨어져 있음

    So, (모든 결정 트리에 걸쳐) 평균적으로 정상 샘플과 적은 단계에서 격리

 

2-4-4 LOF(Local Outlier Factor)

이상치 탐지에 유리

○ 주어진 샘플 주위의 밀도와 이웃 주위의 밀도를 비교

○ 이상치는 종종 k개의 최근접 이웃보다 더 격리됨

 

2-4-5 one-class SVM

특이치 탐지, 고차원 데이터셋에 유리 But 모든 SVM과 마찬가지로 대규모 데이터셋으로의 확장은 어려움

○ 커널 SVM 분류기가 두 클래스를 분리하는 방법(5장)

    ● 모든 샘플을 고차원 공간에(암묵적으로) 매핑 → 이 고차원 공간에서 선형 SVM 분류기를 사용해 두 클래스 분리

○ 여기서는 샘플의 클래스가 1개

    ● 대신 one-class SVM 알고리즘이 원본 공간으로부터 고차원 공간에 있는 샘플을 분리

    ● 원본 공간에서는 모든 샘플을 둘러싼 작은 영역을 찾는 것에 해당

새로운 샘플이 이 영역 안에 놓이지 않는다면 이는 이상치

○ 조정할 파라미터가 적음

○ 커널 SVM을 위한 하이퍼파라미터 하나와 마진 하이퍼파라미터가 존재

○ 마진: 실제 정상인 새로운 샘플을 실수로 이상치로 판단할 확률