2025년 2학기 계량분석 강의 계획

14주차: 요인분석

1. 요인분석의 이론적 이해


1. 요인분석 개요 및 목적


2. 요인분석에 필요한 자료 조건

👉 Python에서도 `factor_analyzer` 패키지로 KMO와 Bartlett 검정을 수행할 수 있음


3. 요인 추출과 분산 개념

✅ 수업 정리

  • 요인분석은 **변수 축약과 잠재 요인 발견**에 유용
  • 자료 조건: 척도(등간/비율), 변수 간 상관관계 필요
  • 적합성 검정: **KMO, Bartlett 검정**으로 가능 여부 확인
  • 요인 추출 방법: **PCA(실무에 많이 사용)**, **CFA(이론 연구에 활용)**

2. 요인의 수 결정 및 회전


1. 요인의 수 결정 방법

👉 **요인 수 결정은 단일 기준이 아니라, 고유값·스크리 도표·설명력 세 가지를 종합적으로 고려**


2. 요인의 회전

✅ 수업 정리 & 토론

  • **정리**
    • 요인의 수 결정 → 고유값 ≥ 1, 스크리 도표, 누적 설명력 기준 활용
    • 요인 회전 → Varimax(독립), Promax(상관 허용)
  • **토론 질문**
    • 연구 데이터에서 요인이 서로 독립적이지 않은 경우, 어떤 회전 방법을 선택해야 할까?
    • 스크리 도표에서 명확한 “팔꿈치”가 보이지 않는다면 어떤 기준으로 요인 수를 정할 수 있을까?

3. Python 실습: 요인분석


0) 패키지

!pip -q install factor_analyzer

1) 데이터·검정·표준화

import pandas as pd, numpy as np, matplotlib.pyplot as plt
from factor_analyzer import FactorAnalyzer
from factor_analyzer.factor_analyzer import calculate_kmo, calculate_bartlett_sphericity
from sklearn.preprocessing import StandardScaler

# 1) 가상 데이터 (10문항, 5점 척도)
df = pd.DataFrame({
    '급여':[4,5,3,4,2,5,4,3,5,4],
    '직장안정성':[5,5,4,5,3,4,5,4,4,5],
    '회사규모':[3,4,4,4,2,3,3,5,4,4],
    '전공관련성':[2,3,5,4,5,2,3,5,4,3],
    '업무내용':[3,4,5,5,4,3,4,5,5,4],
    '발전가능성':[2,3,5,5,4,2,3,5,5,4],
    '미래전망':[4,5,5,4,5,4,5,5,4,5],
    '근로시간':[5,4,2,3,2,5,4,3,2,3],
    '근무환경':[4,5,3,4,3,5,5,4,3,4],
    '출퇴근거리':[5,4,2,3,2,4,3,2,3,4]
})

# 2) 요인분석 적합성: KMO & Bartlett
kmo_all, kmo_model = calculate_kmo(df)
chi2, p_bart = calculate_bartlett_sphericity(df)
print(f"KMO = {kmo_model:.2f}  (권장: ≥0.60)")
print(f"Bartlett p = {p_bart:.4f}  (권장: <0.05)")

# 3) 표준화(권장)
Z = pd.DataFrame(StandardScaler().fit_transform(df), columns=df.columns)

2) 고유값·스크리 플롯(요인 수 결정)

# 초기 요인 수 넉넉하게 넣어 고유값 확인
fa0 = FactorAnalyzer(n_factors=df.shape[1], rotation=None)
fa0.fit(Z)
eigs, _ = fa0.get_eigenvalues()

print("\n[고유값]")
for i, ev in enumerate(eigs, start=1):
    print(f"요인{i}: {ev:.3f}")

# 스크리 플롯
plt.figure(figsize=(7,5))
plt.plot(range(1, len(eigs)+1), eigs, marker='o')
plt.axhline(1, ls='--', c='gray')  # Kaiser 기준선
plt.title("Scree Plot")
plt.xlabel("요인 순서")
plt.ylabel("고유값")
plt.grid(True)
plt.show()

# Kaiser 기준(고유값≥1) 가정: 예시로 3개 선택
n_factors = 3

3) 회전 및 결과표(Varimax/Promax 비교)

# 1) Varimax(직각 회전: 요인 독립 가정)
fa_v = FactorAnalyzer(n_factors=n_factors, rotation='varimax')
fa_v.fit(Z)

# 2) Promax(비직각 회전: 요인 상관 허용)
fa_p = FactorAnalyzer(n_factors=n_factors, rotation='promax')
fa_p.fit(Z)

def tidy_results(fa, name):
    load = pd.DataFrame(fa.loadings_, index=Z.columns,
                        columns=[f"{name}_요인{i+1}" for i in range(n_factors)])
    comm = pd.Series(fa.get_communalities(), index=Z.columns, name=f"{name}_공통성")
    var = pd.DataFrame({
        '고유값': fa.get_factor_variance()[0],
        '비율': fa.get_factor_variance()[1],
        '누적비율': fa.get_factor_variance()[2]
    }, index=[f"{name}_요인{i+1}" for i in range(n_factors)])
    return load, comm, var

load_v, comm_v, var_v = tidy_results(fa_v, "Varimax")
load_p, comm_p, var_p = tidy_results(fa_p, "Promax")

print("\n[Varimax 적재량]")
print(load_v.round(3))
print("\n[Varimax 공통성]")
print(comm_v.round(3))
print("\n[Varimax 설명력]")
print(var_v.round(3))

print("\n[Promax 적재량]")
print(load_p.round(3))
print("\n[Promax 공통성]")
print(comm_p.round(3))
print("\n[Promax 설명력]")
print(var_p.round(3))

해석 체크리스트


4) 요인점수 산출 & 해석(이름 붙이기)

# 요인점수(관찰치별 요인 수준) 계산
# factor_analyzer는 점수 추정을 내부적으로 수행(회귀법). transform 사용.
scores_v = pd.DataFrame(fa_v.transform(Z), columns=[f"F{i+1}_V" for i in range(n_factors)])
scores_p = pd.DataFrame(fa_p.transform(Z), columns=[f"F{i+1}_P" for i in range(n_factors)])

print("\n[요인점수(Varimax) 상위 3행]")
print(scores_v.head(3).round(3))

요인 명명 가이드(예시)

수업 마무리(요약 & 팁)

(선택 과제) 더 탄탄하게 만들기

  1. **평행분석(Parallel Analysis)**로 요인 수를 더 보수적으로 결정
  2. Promax 회전 시 **요인 간 상관행렬**까지 확인
  3. 신뢰도(크론바흐 α)로 요인별 내부일관성 검토 → 하위척도 구성

4. 질의응답 및 요약


1. 최종 정리

요인분석의 목적

요인분석 과정 복습

  1. **적합성 검정**
    • KMO ≥ 0.6, Bartlett p < 0.05 → 요인분석 가능
  2. **요인 수 결정**
    • 고유값 ≥ 1, Scree Plot “팔꿈치 지점”, 누적 설명력 ≥ 60%
  3. **요인 회전**
    • Varimax(직각): 요인 독립 가정
    • Promax(비직각): 요인 간 상관 허용
  4. **결과 해석**
    • 요인 적재량 ≥ 0.4 의미 있음
    • 교차적재 피하기, 공통성 ≥ 0.4 권장
  5. **요인 명명**
    • 적재량 패턴을 보고 요인에 의미 있는 이름 부여

Python 실습 핵심


2. 질의응답