
매번 작은 데이터셋마다 똑같은 무결성 검사(Sanity Check)를 반복하다가 패키지로 만들었습니다
요약
데이터 과학 프로젝트에서 모델의 성능을 검증할 때 반복되는 수동 무결성 검사 과정을 자동화하는 Python 패키지 'modelcheck'를 소개합니다. 이 패키지는 홀드아웃 테스트 점수와 교차 검증 분포를 비교하여 모델 간의 성능 차이가 통계적으로 유의미한지 자동으로 판단합니다.
핵심 포인트
- 모델의 교차 검증 점수 변동성을 분석하여 단일 테스트 결과의 신뢰도를 평가함
- 두 모델의 CV 점수 범위가 겹칠 경우 중첩 경고를 통해 주의를 환기함
- 수동 검증 과정을 패키지화하여 데이터 과학 워크플로우의 효율성을 높임
- 단순 성능 비교를 넘어 통계적 유의성을 고려한 모델 선택을 지원함
데이터 과학 연봉 예측 프로젝트와 Punxsutawney Phil의 그림자가 의미가 있는지 확인하는 프로젝트, 이 두 가지 작은 프로젝트를 작성한 후 저는 두 번 모두 똑같은 수동 단계를 거쳤다는 사실을 깨달았습니다. 바로 몇 개의 모델을 학습시키고, 테스트 세트의 $R^2$를 확인한 다음, 그 수치를 신뢰하기 전에 즉시 교차 검증 (Cross-validation)을 통해 모든 과정을 다시 실행하는 것이었습니다. 수백 개의 행으로 구성된 데이터셋에서는 단 한 번의 훈련/테스트 분할 (Train/test split)만으로도 운 좋게 더 약한 모델이 승자처럼 보일 수 있으며, 저는 이를 매번 수동으로 잡아내고 싶지 않았습니다.
그래서 이 검사 과정을 작은 패키지로 만들었습니다: (https://github.com/DostonUr/modelcheck).
기능
데이터와 모델 딕셔너리 (Dictionary)를 제공하면, 제가 수동으로 하던 비교 작업을 수행합니다:
from sklearn.linear_model import LinearRegression
from sklearn.ensemble import RandomForestRegressor
from modelcheck import compare_regressors
...
이 패키지는 각 모델에 대한 홀드아웃 (Held-out) 테스트 점수, 각 모델의 5-폴드 교차 검증 (5-fold cross-validation) 분포 (평균, 표준편차, 최소값, 최대값)를 보고하며, 제가 실제로 이 패키지를 만든 목적인 다음 두 가지 특정 상황을 자동으로 표시합니다:
- 모델의 교차 검증 점수가 폴드 (Fold)마다 크게 변동하는 경우. 이는 단일 테스트 세트 수치를 정밀한 것으로 신뢰해서는 안 된다는 것을 의미합니다.
- 두 모델의 CV 점수 범위가 심하게 겹치는 경우. 이는 홀드아웃 분할에서 더 높은 점수를 받은 모델이 반드시 실제 승자는 아님을 의미합니다.
단순한 예시가 아닌, 실제로 작동함을 증명하기
저는 이전의 두 프로젝트를 다시 수행할 때 검사 코드를 직접 작성하는 대신 이 패키지를 사용했습니다.
연봉 데이터의 경우, 원래 기사의 수치를 정확히 재현했습니다. 테스트 분할에서 Linear Regression $R^2$ 0.273 대 Random Forest $R^2$ 0.24를 보여주었으며, 이번에는 제가 로직을 수동으로 작성하지 않고도 중첩 경고 (Overlap warning)를 정확하게 생성했습니다.
"선형 회귀 (Linear Regression)"와 "랜덤 포레스트 (Random Forest)"의 CV 점수 범위가 심하게 겹칩니다. 더 높은 평균 $R^2$ 값만으로는 "선형 회귀 (Linear Regression)"가 이 데이터에서 진정으로 더 낫다는 강력한 증거가 되지 않습니다.
그다음 저는 기존 groundhog 기사에서는 하지 않았던 시도를 해보았습니다. 수동으로 계산한 t-검정 (t-test) 대신, Phil의 shadow call을 사용하는 모델과 항상 과거 평균을 예측하는 DummyRegressor를 비교하는 회귀 분석을 설정하고, 두 모델 모두 modelcheck를 통해 실행했습니다. 만약 shadow call이 실제 정보를 담고 있었다면, 이를 사용하는 모델이 dummy 모델을 명확하게 이겼어야 합니다. 하지만 오히려 dummy 베이스라인의 점수가 더 좋았으며 (R² -0.046 대 -0.061), 둘 다 음수였고, 도구는 다시 동일한 중첩 경고 (Overlap warning)를 표시했습니다. 이는 기존 기사에서 얻었던 것과 동일한 "실제 신호(signal)가 없음"이라는 결론에 도달한 것이지만, 완전히 다른 비교 방법을 통해 도출된 결과입니다. 이는 각각의 검사보다 훨씬 더 설득력 있는 확인 방법입니다.
개인용 스크립트로 남겨두지 않고 이것을 공개하는 이유
일회성 스크립트는 제가 코드를 작성할 수 있다는 것만을 증명할 뿐입니다. 다른 사람들이 설치해서 실제로 사용할 수 있는 패키지는 작업물에 대한 차원이 다른 증거가 됩니다. 실제 테스트를 거쳐야 하고, 제가 원래 의도하지 않았던 입력값들도 처리할 수 있어야 하며, 낯선 사람도 바로 사용할 수 있을 만큼 문서화가 잘 되어 있어야 합니다. 작은 도구이지만, 단순히 읽기 위한 것이 아니라 사용하기 위해 만들어졌습니다.
사용해 보세요
pip install git+https://github.com/DostonUr/modelcheck.git
코드, 테스트, 그리고 두 가지 작동 예제: github.com/DostonUr/modelcheck
만약 여러분도 동일한 문제, 즉 작은 데이터셋 때문에 모델이 실제보다 더 좋아 보이는 현상을 겪어보셨다면, 이를 어떻게 해결하셨는지 또는 이 패키지에 무엇이 부족한지에 대해 의견을 듣고 싶습니다. 여기에 답글을 남겨주시거나 
AI 자동 생성 콘텐츠
본 콘텐츠는 Dev.to AI tag의 원문을 AI가 자동으로 요약·번역·분석한 것입니다. 원 저작권은 원저작자에게 있으며, 정확한 내용은 반드시 원문을 확인해 주세요.
원문 바로가기