카이제곱 검정으로 범주형 데이터의 분포와 연관성 분석하기

카이제곱 검정의 적합도·독립성 검정과 분할표 분석 절차를 정리하고, 기대도수·효과크기·표준화 잔차 해석 방법을 다룬다.

2026-08-14 · 최초 발행 2024-04-29

관측 빈도와 기대 빈도의 차이를 읽는 방법

카이제곱 검정(Chi-square test)은 범주별 관측도수 O와 기대도수 E가 얼마나 다른지를 χ² = Σ (O−E)² / E로 계산하는 비모수 검정이다. 표본 수가 충분하면 이 통계량은 카이제곱 분포에 근사한다.

주로 두 가지 질문에 사용한다. 적합도 검정(Goodness-of-fit)은 하나의 범주형 변수가 이론적 또는 목표 분포와 일치하는지 확인한다. 독립성 검정(Test of independence)은 두 범주형 변수 사이에 연관성이 있는지 분할표를 바탕으로 판단한다. 분할표의 셀별 차이와 연관 강도까지 읽어내는 테이블 분석도 이 흐름에 포함된다.

검정 전에 표본이 독립적으로 추출됐는지, 범주가 상호배타적인지 확인해야 한다. 기대도수는 일반적으로 각 셀에서 ≥ 5를 권고하며, 일부 기준에서는 ≥ 1을 허용하되 5 미만인 셀이 20% 미만이어야 한다고 본다. 데이터에서 매개변수를 추정했다면 자유도 보정(ddof)도 필요하다.

희박한 데이터나 2×2 테이블은 별도 판단이 필요하다. 연속성 보정(Yates correction), Fisher의 정확검정, 몬테카를로 p-값 추정을 검토할 수 있다. 우도비 검정(G²)은 대용량 데이터 또는 희박 셀에서 안정적 수렴성을 고려할 때 대안 통계량이 된다.

데이터 설계부터 리포트까지의 검정 흐름

분석의 출발점은 모집단과 표본 설계다. 결측값과 기타 범주를 어떻게 처리할지 정하고, 희박 셀이 생기지 않도록 범주 통합 기준과 과도한 레벨 수 축소 방안을 마련한다.

적합도 검정의 기대도수는 E = N × 가정확률 p로 계산한다. 독립성 검정에서는 E_ij = (행합계_i × 열합계_j) / N을 사용한다. 기대도수 규칙을 충족하지 못하면 범주 통합, 정확검정, 몬테카를로 적용을 검토한다.

통계량, 자유도(df), p-값을 산출한 뒤 유의수준 α와 비교해 기각 여부를 판단한다. 2×2 테이블은 Yates 보정 적용 여부를 검토하고, 설계에 층화가 있다면 층화 카이제곱(Mantel–Haenszel)을 고려한다.

유의성만으로 해석을 마치지 않는다. Phi와 Cramer’s V는 연관 강도를 정량화하고, 표준화 잔차는 어떤 셀이 결과에 크게 기여했는지 보여 준다. 여러 셀을 비교할 때는 FDR(BH) 또는 Bonferroni 보정으로 2차 해석의 과탐지를 제어한다.

운영 환경에서는 코드 템플릿, 로그와 감사 추적, 랜덤 시뮬레이션의 seed 고정을 함께 관리하는 편이 낫다. 결과 리포트에는 통계량, df, p-값, 효과크기, 가정 점검 결과, 잔차 하이라이트를 포함한다.

목표 분포와 실제 분포를 비교할 때

적합도 검정에는 범주별 관측도수 O와 이론·목표 확률 p 또는 기대도수 E가 입력으로 들어간다. E = N × p를 계산한 뒤 χ² = Σ (O−E)²/E를 구하고, 자유도는 (범주수 − 1 − 추정모수수)로 산출한다.

희박 셀이 있으면 범주를 통합하거나 몬테카를로 p-값을 사용할 수 있다. 확률 p를 데이터에서 추정한 경우에는 ddof 보정이 필요하다.

전제조건: Python 3.10+, SciPy 1.11+, pandas 2.x / R 4.2+

Python

import numpy as np
from scipy.stats import chisquare

# 관측: 3개 범주, 목표 비율 p = [0.5, 0.3, 0.2]
obs = np.array([52, 29, 19])
p   = np.array([0.5, 0.3, 0.2])
N   = obs.sum()
exp = N * p

# 모수(확률) 외부 지정 → ddof=0, 내부 추정 시 ddof 설정
res = chisquare(f_obs=obs, f_exp=exp, ddof=0)
print(res.statistic, res.pvalue)

R

obs <- c(52, 29, 19)
p   <- c(0.5, 0.3, 0.2)
chisq.test(x = obs, p = p, rescale.p = TRUE)  # p 합이 1이 아니면 rescale.p=TRUE

분할표에서 변수 간 연관성을 검정할 때

독립성 검정은 r×c 분할표의 관측도수 X를 입력으로 사용한다. 각 셀의 기대도수 E_ij = (row_i sum × col_j sum)/N을 계산하고, χ² = Σ (O−E)²/E와 df = (r−1)(c−1)을 통해 p-값을 구한다.

2×2 테이블에서 기대도수가 작다면 Fisher 정확검정을 적용할 수 있다. 연속성 보정 여부(correction)는 데이터 크기와 희박성을 기준으로 결정한다.

Python

import numpy as np
from scipy.stats import chi2_contingency, fisher_exact

tbl = np.array([[30, 20],
                [25, 25]])

# 독립성 카이제곱 (2x2: 연속성 보정은 상황별 선택)
chi2, p, dof, exp = chi2_contingency(tbl, correction=False)
print(chi2, p, dof)
# 효과크기: Cramer's V
n = tbl.sum()
r, k = tbl.shape
cramers_v = (chi2 / (n * (min(r-1, k-1)))) ** 0.5
print(cramers_v)

# 기대도수 작을 때: Fisher
oddsratio, p_fisher = fisher_exact(tbl, alternative='two-sided')
print(oddsratio, p_fisher)

R

tbl <- matrix(c(30,20,25,25), nrow=2, byrow=TRUE)
chisq.test(tbl, correct=FALSE)     # Yates 보정 미적용
fisher.test(tbl)                   # 희박 데이터 대응

잔차와 효과크기로 셀별 의미를 해석하기

표준화 잔차(Standardized residual)는 (O−E)/sqrt(E)로 계산한다. |잔차| ≥ 2인 셀은 결과에 대한 기여가 크다고 판단하며, 여러 셀을 비교할 때는 FDR 보정을 적용한다.

연관 강도는 2×2 테이블에서 Phi, r×c 테이블에서 Cramer’s V로 표현한다. Cohen의 해석 가이드는 0.1을 작은 효과, 0.3을 중간 효과, 0.5를 큰 효과로 제시하며 문맥에 따라 조정할 수 있다. 2×2 테이블에서는 오즈비(OR)와 신뢰구간을 함께 제시해 연관의 방향과 크기를 보완한다. 층화가 있다면 Mantel–Haenszel OR도 검토 대상이다.

Python

import numpy as np
from scipy.stats import chi2_contingency

tbl = np.array([[40, 10, 5],
                [20, 15, 10]])

chi2, p, dof, exp = chi2_contingency(tbl, correction=False)
std_resid = (tbl - exp) / np.sqrt(exp)

# Cramer's V
n = tbl.sum()
r, k = tbl.shape
cramers_v = (chi2 / (n * (min(r-1, k-1)))) ** 0.5

print("p-value:", p)
print("Std residuals:\n", np.round(std_resid, 2))
print("Cramer's V:", round(cramers_v, 3))

R

tbl <- matrix(c(40,10,5, 20,15,10), nrow=2, byrow=TRUE)
fit <- chisq.test(tbl, correct=FALSE)
std.resid <- (tbl - fit$expected) / sqrt(fit$expected)
fit$p.value; round(std.resid, 2)

검정 선택부터 결과 보고까지

적합도독립성아니오입력: 관측도수 O, 설계 가정데이터 점검: 결측/희박/범주통합 여부검정 유형 선택기대도수 E = N×p 계산분할표 기대도수 E_ij =(row×col)/Nχ² = Σ (O−E)^2/E, df 계산가정 위반 여부대안: Fisher/Monte Carlo,범주 통합, 연속성 보정효과크기 산출: Phi/Cramer'sV사후 분석: 표준화 잔차,다중비교 보정출력: χ², df, p, 효과크기,잔차 리포트
항목 적합도 검정 독립성 검정 테이블 분석(잔차·효과크기)
성능 O(k) 계산 복잡도, 매우 경량 O(r×c), 실무 데이터에서 경량 χ² 계산 후 후처리 잔차·지표 계산 소폭 추가
확장성 범주수 증가 시 기대도수 희박성 주의 대규모 분할표에서 희박성·해석 복잡도 증가 고차원 표는 시각·요약 필요, 셀 통합 전략 필수
일관성 가정 충족 시 보수적 Type I 제어 표본 크기 적절 시 안정적 잔차/효과크기 조합으로 해석 일관성 향상
안정성 희박 데이터 시 몬테카를로 권장 2×2 희박 시 Fisher 권장 다중 비교 보정으로 과탐지 억제
운영 편의 목표분포 명시 시 자동화 용이 표준 라이브러리로 일괄 처리 간단 리포트 템플릿화로 의사결정 속도 향상

현업 데이터에 연결하는 방식

마케팅에서는 캠페인 노출 대비 클릭 분포가 기대 비율과 일치하는지 적합도 검정으로 점검할 수 있다. 목표 분포에서 벗어났다면 채널 또는 소재 재배분의 근거로 활용한다.

제조 공정에서는 불량 코드 분포가 목표 비율과 다른지 확인하고, 표준화 잔차로 이상 기여 셀을 찾아 라인별 교정에 연결할 수 있다.

고객 세그먼트와 구매 전환의 관계는 독립성 검정으로 평가한다. Cramer’s V로 효과크기를 제시하고 OR로 실무 해석을 보완한다. 의료 데이터의 치료군 × 결과(호전/비호전) 테이블도 같은 방식으로 분석하되, 층화 혼란변수를 통제하고 필요하면 Fisher를 적용한다.

표본 규모와 재현성을 함께 관리하기

효과크기 w(Cohen)를 사용하면 대략적인 표본 크기를 N ≈ (Z*{1−α/2}+Z*{1−β})² / w²로 산정할 수 있다. 예) α=0.05, Power=0.8, w=0.1 → N≈784. 다중 비교 보정을 적용하면 거짓발견률(FDR)을 ≤ 목표치로 통제할 수 있다.

가설 검정에 효과크기와 잔차를 결합하면 결과의 설명 가능성이 높아진다. 표준화된 분석 파이프라인은 의사결정 시간을 줄이고 재현성과 감사 추적성을 확보하는 기반이 된다.

카이제곱 검정적합도 검정독립성 검정분할표통계 분석