Skip to main content

가설검정

가설검정(Hypothesis Testing)은 데이터에 기반하여 주장의 타당성을 통계적으로 판단하는 프레임워크입니다. “두 그룹의 평균이 다른가?”, “변수 간에 관련이 있는가?”와 같은 질문에 수학적으로 답할 수 있습니다.

학습 목표

  • 귀무가설과 대립가설을 설정할 수 있다
  • p-value의 의미를 정확히 해석할 수 있다
  • 독립표본 t-test로 두 그룹의 평균을 비교할 수 있다
  • 카이제곱 검정으로 범주형 변수 간 관련성을 검정할 수 있다
  • ANOVA로 세 그룹 이상의 평균을 비교할 수 있다

왜 중요한가

직관이나 시각화만으로는 차이가 실제인지, 우연인지 판단하기 어렵습니다. 가설검정은 “이 차이가 통계적으로 유의미한가?”에 대한 객관적 기준을 제공합니다. A/B 테스트, 모델 성능 비교, 피처 유의성 검증 등 데이터 분석의 핵심 도구입니다.

가설검정의 프레임워크

용어설명예시
귀무가설(H0)차이가 없다, 효과가 없다”A/B 그룹의 전환율은 같다”
대립가설(H1)차이가 있다, 효과가 있다”A/B 그룹의 전환율은 다르다”
유의수준(alpha)귀무가설을 잘못 기각할 확률보통 0.05 (5%)
p-value귀무가설이 참일 때 관측된 결과가 나올 확률작을수록 귀무가설에 반하는 증거
p-value는 “효과의 크기”를 알려주지 않습니다. p < 0.05라고 해서 실무적으로 의미 있는 차이라고 단정할 수 없습니다. 항상 효과 크기(effect size)와 함께 해석하세요.

독립표본 t-test

두 독립 그룹의 평균 차이를 검정합니다.
import numpy as np
import pandas as pd
from scipy import stats

np.random.seed(42)

# 두 그룹의 연봉 데이터
group_a = np.random.normal(4500, 800, 50)   # A팀 연봉
group_b = np.random.normal(4800, 900, 50)   # B팀 연봉

# H0: A팀과 B팀의 평균 연봉은 같다
# H1: A팀과 B팀의 평균 연봉은 다르다

# 독립표본 t-test
t_stat, p_value = stats.ttest_ind(group_a, group_b)
print(f"t-통계량: {t_stat:.3f}")
print(f"p-value: {p_value:.4f}")

if p_value < 0.05:
    print("→ 귀무가설 기각: 두 그룹의 평균 연봉에 유의미한 차이가 있습니다")
else:
    print("→ 귀무가설 기각 실패: 두 그룹의 평균 연봉에 유의미한 차이가 없습니다")

# 효과 크기 (Cohen's d)
pooled_std = np.sqrt((group_a.std()**2 + group_b.std()**2) / 2)
cohens_d = (group_b.mean() - group_a.mean()) / pooled_std
print(f"Cohen's d: {cohens_d:.3f}")
# |d| < 0.2: 작은 효과, 0.2~0.8: 중간 효과, > 0.8: 큰 효과

대응표본 t-test

동일 대상의 전/후 비교에 사용합니다.
# 교육 전후 성과 비교
before = np.random.normal(70, 10, 30)
after = before + np.random.normal(5, 8, 30)  # 평균 5점 향상

# H0: 교육 전후 성과에 차이가 없다
t_stat, p_value = stats.ttest_rel(before, after)
print(f"대응표본 t-test p-value: {p_value:.4f}")
print(f"평균 변화: {(after - before).mean():.1f}점")

카이제곱 검정

범주형 변수 간의 독립성을 검정합니다.
# 부서와 이직 여부의 관련성 검정
np.random.seed(42)
data = pd.DataFrame({
    'department': np.random.choice(['개발', '영업', '마케팅'], 300),
    'turnover': np.random.choice(['이직', '잔류'], 300, p=[0.3, 0.7])
})

# 교차표 생성
contingency = pd.crosstab(data['department'], data['turnover'])
print("교차표:")
print(contingency)

# 카이제곱 검정
chi2, p_value, dof, expected = stats.chi2_contingency(contingency)
print(f"\n카이제곱 통계량: {chi2:.3f}")
print(f"자유도: {dof}")
print(f"p-value: {p_value:.4f}")

if p_value < 0.05:
    print("→ 부서와 이직 여부 사이에 유의미한 관련이 있습니다")
else:
    print("→ 부서와 이직 여부 사이에 유의미한 관련이 없습니다")

# 기대빈도
print("\n기대빈도:")
print(pd.DataFrame(expected, index=contingency.index,
                   columns=contingency.columns).round(1))

ANOVA — 다중 그룹 비교

세 그룹 이상의 평균 차이를 동시에 검정합니다.
# 세 부서의 성과 점수 비교
np.random.seed(42)
dev_scores = np.random.normal(78, 10, 40)
sales_scores = np.random.normal(72, 12, 40)
mkt_scores = np.random.normal(75, 11, 40)

# 일원배치 ANOVA
# H0: 세 부서의 평균 성과 점수는 같다
f_stat, p_value = stats.f_oneway(dev_scores, sales_scores, mkt_scores)
print(f"F-통계량: {f_stat:.3f}")
print(f"p-value: {p_value:.4f}")

if p_value < 0.05:
    print("→ 적어도 하나의 부서 평균이 다릅니다")
    # 사후검정 (Tukey HSD)으로 어떤 쌍이 다른지 확인
    from scipy.stats import tukey_hsd
    result = tukey_hsd(dev_scores, sales_scores, mkt_scores)
    print(result)
else:
    print("→ 세 부서의 평균 성과에 유의미한 차이가 없습니다")
ANOVA는 “차이가 있는지”만 알려줍니다. “어떤 그룹 간에 차이가 있는지”는 사후검정(Tukey HSD, Bonferroni 등)으로 확인해야 합니다.

검정 선택 가이드

상황검정 방법scipy 함수
두 그룹 평균 비교 (독립)독립표본 t-testttest_ind()
두 그룹 평균 비교 (대응)대응표본 t-testttest_rel()
세 그룹 이상 평균 비교일원배치 ANOVAf_oneway()
범주형 변수 독립성카이제곱 검정chi2_contingency()
정규성 검정Shapiro-Wilkshapiro()
등분산 검정Levenelevene()

오류 유형과 검정력

H0이 참H0이 거짓
H0 기각1종 오류 (alpha)올바른 판단 (검정력)
H0 기각 실패올바른 판단2종 오류 (beta)
# 검정력 계산 예시
from scipy.stats import norm

# 효과크기, 표본크기, 유의수준으로 검정력 계산
def compute_power(effect_size, n, alpha=0.05):
    """검정력을 계산합니다."""
    z_alpha = norm.ppf(1 - alpha/2)
    z_beta = effect_size * np.sqrt(n) - z_alpha
    power = norm.cdf(z_beta)
    return power

# 표본 크기에 따른 검정력 변화
for n in [10, 30, 50, 100, 200]:
    power = compute_power(0.3, n)
    print(f"  n={n:3d}: 검정력 = {power:.3f}")

AI/ML에서의 활용

  • A/B 테스트: 모델 A와 B의 성능 차이가 통계적으로 유의미한지 검정합니다
  • 피처 선택: 카이제곱 검정으로 범주형 피처와 타겟 간의 관련성을 평가합니다
  • 모델 비교: 교차 검증 결과에 대해 대응표본 t-test로 모델 간 성능 차이를 검정합니다
  • 실험 설계: 필요한 표본 크기를 검정력 분석으로 결정합니다
아닙니다. p > 0.05는 “차이가 없다”가 아니라 “현재 데이터로는 차이를 입증할 수 없다”는 의미입니다. 표본이 부족하거나 효과 크기가 작을 때 p-value가 높게 나올 수 있습니다.
Welch’s t-test(stats.ttest_ind(equal_var=False))를 사용하세요. 등분산을 가정하지 않는 버전으로, scipy의 기본 설정은 equal_var=True이므로 명시적으로 지정해야 합니다.

체크리스트

  • 귀무가설과 대립가설을 설정할 수 있다
  • p-value의 의미를 정확히 해석할 수 있다
  • 상황에 맞는 검정 방법을 선택할 수 있다
  • 독립표본 t-test를 실행하고 결과를 해석할 수 있다
  • 카이제곱 검정으로 범주형 변수의 독립성을 검정할 수 있다
  • 1종 오류와 2종 오류의 차이를 설명할 수 있다

다음 문서