[개인 경진대회] Kaggle Playground Series S6E6 연구 (7): 193번째 프라이빗 일반화 후보 연구

2026. 6. 29. 10:15·6. 경진 대회 (kaggle, dacon 등)/6-1 연구 및 개선 기록

안녕하세요!

이번 글에서는 Kaggle Playground Series Season 6 Episode 6에서 프라이빗 성능을 우선으로 만든 193번 제출 후보를 정리해 보겠습니다.

 

현재 최종 파일은 다음과 같습니다.

  • 193_PRIVATE_CV_oof970659.csv
  • OOF Balanced Accuracy: 0.9706589608

여기서 먼저 주의할 점이 있습니다. 0.970659는 프라이빗 리더보드 점수가 아니라, train data의 정답을 이용해 계산한 OOF 점수입니다. 프라이빗 test의 정답은 대회 종료 전까지 알 수 없기 때문에 실제 프라이빗 점수를 미리 계산할 수는 없습니다.

 

따라서 이번 연구의 목적은 public leaderboard 점수를 직접 올리는 것이 아니었습니다. public 점수를 전혀 사용하지 않고, OOF 점수와 여러 fold에서의 안정성, class별 recall, 취약 subset의 손실을 함께 확인하여 숨겨진 private test에서도 버틸 가능성이 높은 후보를 고르는 것이 목적이었습니다.

 

깃허브 주소: https://github.com/gonida1010/Kaggle_Predicting_Stellar_Class

 

GitHub - gonida1010/Kaggle_Predicting_Stellar_Class: Kaggle Playground Series S6E6 Predicting Stellar Class 대회를 위한 연

Kaggle Playground Series S6E6 Predicting Stellar Class 대회를 위한 연구 저장소입니다. - gonida1010/Kaggle_Predicting_Stellar_Class

github.com


1. OOF 점수만으론 부족

처음에는 OOF Balanced Accuracy가 가장 높은 후보를 선택하면 된다고 생각하기 쉽습니다.

하지만 실제 실험에서는 점수가 조금 더 높은 후보가 특정 class나 특정 데이터 구간을 크게 망가뜨리는 경우가 있었습니다. 전체 평균에서는 좋아 보여도 spectral type, galaxy population, redshift, 색지수 구간으로 나누어 보면 성능이 내려가는 후보가 있었습니다.

 

Balanced Accuracy는 GALAXY, QSO, STAR의 recall 평균입니다.

 

클래스 수가 많은 GALAXY만 잘 맞춘다고 점수가 높아지는 구조가 아닙니다. 상대적으로 수가 적은 QSO와 STAR의 recall도 같은 비중으로 반영됩니다. 그래서 전체 정확도뿐 아니라 class별 recall 변화까지 같이 봐야 했습니다.

 

또 한 가지 문제는 같은 OOF 전체에서 후보를 계속 선택하면 작은 차이에 과적합될 수 있다는 점이었습니다. 이를 줄이기 위해 후보를 여러 개의 meta-fold로 다시 나누고, 일부 fold에서만 좋아진 것인지 반복해서 확인했습니다.

 

이번 후보 선택에서는 다음 항목을 함께 사용했습니다.

  • 전체 OOF Balanced Accuracy
  • 기준 후보 대비 점수 변화
  • class별 recall의 최악 변화
  • 취약 subset의 최악 변화
  • 여러 meta-fold에서 개선된 비율
  • 기존 안정 후보에서 변경된 train/test row 수

단순히 가장 높은 숫자를 선택한 것이 아니라, 점수 상승과 변경 범위를 같이 제한하는 방식으로 접근했습니다.


2. 193번까지 이어진 후보의 계보

193번은 처음부터 새 모델 하나를 학습해서 바로 나온 결과가 아닙니다. 이전까지 만든 안정 후보를 시작점으로 두고, 아주 작은 수정만 반복해서 추가한 결과입니다.

이날 시작점은 95번 후보였습니다.

95번은 56번 TE disagreement 후보와 90번 subset guard 후보의 장점을 특정 good subset에서 결합한 후보였습니다. OOF는 0.9706450214였습니다.

그 다음 171번에서는 weak O/B 구간을 84번 classwise research blend의 예측으로 되돌렸습니다.

  • 95번: 0.9706450214
  • 171번: 0.9706515037

O/B 계열은 이전 subset 분석에서도 모델이 어려워하던 구간이었습니다. 전체 예측을 크게 바꾸지 않고, 두 후보가 다르게 판단한 row 중 weak O/B 조건에 해당하는 부분만 rollback했습니다.

 

그 다음 181번에서는 일반 CatBoost + RealMLP식 feature 모델의 QSO 확률을 0.5%만 섞었습니다.

  • 171번: 0.9706515037
  • 181번: 0.9706563117

마지막으로 193번에서는 one-vs-rest CatBoost + RealMLP식 feature 모델의 GALAXY 확률을 0.5%만 추가했습니다.

  • 181번: 0.9706563117
  • 193번: 0.9706589608

흥미로운 점은 보조 모델인 one-vs-rest CatBoost의 단독 OOF가 0.9691523963으로 181번보다 낮았다는 것입니다.

단독 점수가 낮다고 해서 쓸모없는 모델은 아니었습니다. 이 모델은 GALAXY와 나머지 class를 따로 구분하는 이진 분류 구조로 학습했습니다. 전체 argmax 성능은 낮아도 GALAXY 확률에는 기존 후보와 다른 정보가 남아 있었습니다.

 

즉 좋은 앙상블 재료는 반드시 단독 점수가 가장 높은 모델일 필요가 없었습니다. 현재 모델이 틀리는 row에서 다른 방향의 정보를 제공할 수 있는지가 더 중요했습니다.

 

단일 모델과 누적 연구 후보의 OOF 점수 비교


3. GALAXY 확률 0.5%만 섞은 이유

193번의 마지막 보정은 다음과 같은 방식입니다.

  1. 181번 후보의 GALAXY 확률을 가져옵니다.
  2. one-vs-rest CatBoost + RealMLP식 feature 모델의 GALAXY 확률을 0.5%만 섞습니다.
  3. GALAXY, QSO, STAR 확률의 합이 다시 1이 되도록 정규화합니다.
  4. 가장 높은 확률을 가진 class를 최종 예측으로 선택합니다.

수식으로 표현하면 다음과 같습니다.

new_GALAXY = 0.995 × current_GALAXY
           + 0.005 × OVR_CatBoost_GALAXY

QSO와 STAR 확률을 직접 크게 흔드는 방식이 아니라, GALAXY 경계에 보조 모델의 신호를 아주 조금 추가한 것입니다.

0.5%는 후보 탐색에서 사용한 가장 작은 alpha였습니다. alpha는 0.005부터 0.055까지 0.005 간격으로 확인했습니다.

 

가중치가 너무 크면 보조 모델의 단독 오류까지 현재 후보로 들어옵니다. 반대로 너무 작으면 최종 class가 바뀌는 row가 거의 없습니다. 이번에는 0.005만으로 train 예측 3개, test 예측 1개가 181번과 달라졌습니다.

정말 작은 변화입니다.

 

그런데 이 작은 변화로 OOF가 0.9706563117에서 0.9706589608로 상승했습니다. 큰 모델을 새로 섞은 것이 아니라, 기존 안정 후보의 결정 경계에 GALAXY 전용 보조 신호를 아주 약하게 추가한 결과였습니다.


4. 24개 source와 1,199개 후보를 어떻게 비교했는가

이날 사용 가능한 OOF/test probability source는 24개였습니다.

여기에는 우리가 직접 학습한 LightGBM, XGBoost, CatBoost, one-vs-rest CatBoost, fold-safe target encoding 모델과 공개된 RealMLP, TabM, logistic stacker 계열이 포함되어 있었습니다. 이전 연구에서 만든 56, 68, 69, 84, 85, 90번 후보도 하나의 source로 다시 사용했습니다.

 

연구 후보가 다음 연구의 재료가 된 셈입니다.

각 source에 대해 다음 세 종류의 후보를 만들었습니다.

  1. class-wise probability blend
  2. 취약 subset을 이전 안정 후보로 되돌리는 rollback
  3. 성능이 좋았던 subset만 다른 후보에서 가져오는 transfer

이 과정에서 총 1,199개의 후보가 생성됐습니다.

처음에는 전체 OOF, class recall, subset 손실과 test 변경량을 이용해 빠르게 순위를 정했습니다. 이후 상위 120개만 정밀 검사했습니다.

 

정밀 검사에서는 5-fold를 10개의 다른 random seed로 반복했습니다. 따라서 후보 하나당 총 50개의 meta validation 구간에서 기준 후보보다 좋아졌는지 확인했습니다.

193번은 56번 reference와 비교했을 때 50개 meta-fold 모두에서 점수가 높았습니다.

  • reference 대비 평균 delta: +0.0000863677
  • reference 대비 최소 meta-fold delta: +0.0000102667
  • reference 대비 positive fold rate: 1.0

최소 delta도 양수라는 점이 중요했습니다.

일부 fold에서 크게 오르고 다른 fold에서 떨어진 결과가 아니라, 확인한 모든 meta-fold에서 reference보다 높았습니다.

181번과 직접 비교했을 때는 positive rate가 0.5였습니다. 하지만 181번 대비 train prediction이 3개만 달라졌기 때문에, 나머지 fold에서는 두 후보의 점수가 동일하게 나온 경우가 많았습니다. 이때 최소 delta는 0이었고 음수 fold는 없었습니다.

1,199개 후보 중 상위 120개를 안정성 기준으로 재정렬한 결과


5. 전체 점수보다 class와 subset을 다시 확인했습니다

193번의 class별 결과는 다음과 같습니다.

GALAXY
precision  0.990797
recall     0.960276
F1         0.975298

QSO
precision  0.951879
recall     0.977207
F1         0.964377

STAR
precision  0.883586
recall     0.974493
F1         0.926816

 

GALAXY recall만 올리고 QSO 또는 STAR를 크게 희생한 후보는 아니었습니다.

56번 reference와 비교한 subset 결과도 확인했습니다.

weak O/B: +0.000844
weak mag_range bin 2: +0.000465
weak g-i bin 2: +0.000492
good redshift bin 2: +0.000254
good A/F Blue Cloud: +0.000642
good magnitude bin 0: +0.001280
weak core 전체: +0.000147
good core 전체: +0.000093

 

모든 subset이 오른 것은 아니었습니다. weak u-r bin 6은 -0.000032, high g-i 구간은 -0.000032 정도 내려갔습니다. M 계열을 포함한 good M subset에서는 -0.000140이 최악의 변화였습니다.

 

이 손실을 숨기지 않고 robust score에 penalty로 넣었습니다.

최종 robust score는 전체 OOF 상승만 보는 것이 아니라, 최악 meta-fold, 최악 subset, 최악 class recall과 test 변경량까지 함께 반영했습니다.

 

193번의 final robust score는 0.0000477647로 전체 후보 중 가장 높았습니다.

6. OOF가 더 높은 192번을 선택하지 않은 이유

193번을 고를 때 가장 고민했던 후보는 192번이었습니다.

192번의 OOF는 0.970664로 193번의 0.970659보다 조금 더 높았습니다. OOF 숫자 하나만 보면 192번을 선택해야 합니다.

하지만 192번은 weak g-i bin 2 구간을 69번 guarded research stack으로 되돌리는 공격적인 rollback 후보였습니다.

  • 192번 reference 대비 변경: 303 rows
  • 192번 test 변경: 130 rows
  • 193번 reference 대비 변경: 192 rows
  • 193번 test 변경: 85 rows
  • 193번 181번 대비 변경: train 3 rows, test 1 row

192번은 더 많은 row를 바꾸면서 더 높은 OOF를 얻었습니다. 반면 193번은 직전 안정 후보를 거의 유지한 상태에서 OOF를 조금 더 올렸습니다. 숨겨진 private set에서는 OOF에서 고른 특정 subset 규칙이 그대로 맞는다는 보장이 없습니다. 특히 수백 개의 후보를 탐색한 뒤 가장 높은 OOF만 선택하면 OOF 자체에 과적합될 위험이 있습니다.

 

그래서 raw OOF가 아주 조금 높은 192번보다, 반복 fold와 subset 검사에서 더 안정적이고 변경량도 작은 193번을 최종 private 후보로 유지했습니다. 이 선택은 “OOF가 낮아도 괜찮다”는 뜻은 아닙니다.

 

OOF가 충분히 높다는 조건을 먼저 만족한 뒤, 차이가 매우 작을 때는 더 적은 변경과 더 안정적인 fold 결과를 우선했다는 뜻입니다.


마무리

이번 연구에서 가장 크게 느낀 점은 앙상블의 목적이 무조건 여러 모델을 많이 섞는 것이 아니라는 점입니다.

193번은 24개 모델을 모두 크게 섞은 결과가 아닙니다. 이미 안정적인 후보 위에 전체 점수는 조금 낮지만 다른 구조로 학습된 one-vs-rest CatBoost의 GALAXY 신호를 0.5%만 추가했습니다.

그리고 그 작은 변화가 우연히 전체 OOF에서만 좋아진 것인지 확인하기 위해 50개의 meta-fold, class recall, 14개의 주요 subset, 변경 row 수를 다시 검사했습니다.

 

public leaderboard 점수를 직접 사용하지 않았기 때문에 public 최적화 후보보다 점수가 낮게 보일 수 있습니다. 하지만 이번 후보의 목적은 public 순위를 최대화하는 것이 아니라, 숨겨진 private test에서도 유지될 가능성이 높은 일반화 후보를 만드는 것이었습니다.

결국 마지막에 남긴 기준은 단순했습니다.

  • OOF는 충분히 높아야 합니다.
  • 모든 class recall을 같이 봐야 합니다.
  • 특정 subset의 큰 손실을 확인해야 합니다.
  • 여러 fold에서 같은 방향으로 좋아져야 합니다.
  • 비슷한 점수라면 test 예측을 덜 바꾸는 후보가 더 안전합니다.
그리고 아직 실험을 안 해본 목록들이 있습니다. 아래에 추가로 적어놔 보겠습니다. 지금 현재 6월 29일 14시경쯤, "강한 CatBoost와 SDSS 저가중치 학습"을 구현하고 실행중에 있습니다!

남은 일반화 연구의 실행 순서

  1. 강한 CatBoost와 SDSS 저가중치 학습
    • 현재 직접 학습 CatBoost 최고인 RealMLP식 비누수 피처 모델을 기준으로 사용합니다.
    • SDSS는 학습 fold에만 추가하고 competition validation fold에는 넣지 않습니다.
    • weight 0.00, 0.03, 0.06, 0.10을 같은 fold로 비교합니다.
    • paired fold 평균, 최악 fold, class recall을 통과한 weight만 5-fold 전체 검증으로 보냅니다.
  2. 상관성과 다양성을 제한조건으로 둔 class-wise stacker
    • 단순 OOF 최대화가 아니라 fold별 개선 일관성과 모델 간 상관성을 함께 사용합니다.
    • 현재 최고 193_PRIVATE_CV_oof970659.csv를 넘어도 최악 fold가 무너지면 채택하지 않습니다.
  3. 확장 fold-safe target-stat feature bank
    • 범주별 class mean뿐 아니라 count, frequency, entropy와 compact interaction을 fold 내부에서만 계산합니다.
    • validation과 test 변환에는 해당 fold train 통계만 사용합니다.
  4. RealMLP v5 직접 학습
    • 공개 OOF를 복사하지 않고 로컬 5-fold OOF와 test probability를 직접 생성합니다.
    • embedding, robust preprocessing, ensemble, EMA, label smoothing을 단계별로 분리 검증합니다.
  5. one-vs-rest TabM 직접 학습
    • class별 이진 OOF를 생성하고 class-wise logistic 결합을 검증합니다.
    • 직접 RealMLP와의 오류 상관성이 낮을 때만 stacker 재료로 채택합니다.
  6. nested transition/subset logit calibration
    • 기존 OOF를 같은 OOF로 다시 튜닝하는 낙관 편향을 막기 위해 바깥 fold에서만 평가합니다.
    • 전체 OOF뿐 아니라 class recall과 취약 subset의 최악 성능도 함께 제한합니다.

각 단계의 결과는 해당 날짜 notes 폴더와 실험 artifacts 폴더에 CSV, JSON, 그래프, 판단 메모로 저장합니다. 한 단계가 채택 또는 폐기된 뒤 다음 단계로 이동합니다.

 

이상으로 캐글 경진 대회에 대해서 7번째 블로그를 정리해봤습니다. 얼른 프라이빗 점수가 공개되면 좋겠습니다. 아, 아니군요 아직 6번의 실험이 남았으니, 이틀만 더 달리면 되겠습니다 ㅎㅎ...

 

깃허브 주소: https://github.com/gonida1010/Kaggle_Predicting_Stellar_Class

 

GitHub - gonida1010/Kaggle_Predicting_Stellar_Class: Kaggle Playground Series S6E6 Predicting Stellar Class 대회를 위한 연

Kaggle Playground Series S6E6 Predicting Stellar Class 대회를 위한 연구 저장소입니다. - gonida1010/Kaggle_Predicting_Stellar_Class

github.com

'6. 경진 대회 (kaggle, dacon 등) > 6-1 연구 및 개선 기록' 카테고리의 다른 글

[개인 경진대회] Kaggle Playground S6E6 최종 결과, public보다 OOF를 선택한 이유 (2824팀중 상위 1%)  (0) 2026.07.01
[개인 경진대회] DACON - 성균관대 멀티모달 AI 챌린지 (마무리2) - Private 1등, 최종 v44 회고  (0) 2026.07.01
[개인 경진 대회] Kaggle Playground Series S6E6 연구 (6): RealMLP 피처 뱅크 실험 기록  (0) 2026.06.27
[개인 경진대회] DACON - 성균관대 멀티모달 AI 챌린지 (마무리1) - Private 1등  (0) 2026.06.25
[개인 경진 대회] Kaggle Playground Series S6E6 연구 (5): RealMLP 피처 뱅크 실험 기록  (0) 2026.06.19
'6. 경진 대회 (kaggle, dacon 등)/6-1 연구 및 개선 기록' 카테고리의 다른 글
  • [개인 경진대회] Kaggle Playground S6E6 최종 결과, public보다 OOF를 선택한 이유 (2824팀중 상위 1%)
  • [개인 경진대회] DACON - 성균관대 멀티모달 AI 챌린지 (마무리2) - Private 1등, 최종 v44 회고
  • [개인 경진 대회] Kaggle Playground Series S6E6 연구 (6): RealMLP 피처 뱅크 실험 기록
  • [개인 경진대회] DACON - 성균관대 멀티모달 AI 챌린지 (마무리1) - Private 1등
고니3000원
고니3000원
프로젝트의 구현 과정과 기술적 노하우를 담았습니다. AI 모델 연구와 매일의 학습 기록을 차곡차곡 공유하고 있습니다.
  • 고니3000원
    곤이의 공부 블로그
    고니3000원
  • 전체
    오늘
    어제
    • 분류 전체보기 (231)
      • 1. AI 논문 + 모델 분석 (22)
        • AI 논문 분석 (13)
        • AI 모델 분석 (9)
      • 2. 자료구조와 알고리즘 (16)
        • 2-1 자료구조와 알고리즘 (13)
        • 2-2 강화학습 알고리즘 (3)
      • 3. 자습 & 메모(실전, 실습, 프로젝트) (27)
        • 3-1 문제 해석 (4)
        • 3-2 메모(실전, 프로젝트) (14)
        • 3-3 배포 실전 공부 (7)
        • 3-4 최신 기술 분석 (2)
      • 4. [팀] 프로젝트 및 공모전 (31)
        • 4-1 팀 프로젝트(메모, 공부) (1)
        • 4-2 Meat-A-Eye (6)
        • 4-3 RL-Tycoon-Agent (3)
        • 4-4 구조물 안정성 물리 추론 AI 경진대회(D.. (4)
        • 4-5 AgentShield(보안 플랫폼) (17)
      • 5. [개인] 프로젝트 및 공모전 (25)
        • 4-1 귀멸의칼날디펜스(자바스크립트 활용) (5)
        • 4-2 바탕화면 AI 펫 프로그램 (4)
        • 4-3 개인 프로젝트(기타) (3)
        • 4-4 공모전 (9)
        • 4-5 나만의 로컬 LLM 멀티 에이전트 구축 (4)
      • 6. 경진 대회 (kaggle, dacon 등) (12)
        • 6-1 연구 및 개선 기록 (11)
        • 6-2 공유 코드 분석하기 (1)
      • 개념 정리 step1 (32)
        • Python 기초 (7)
        • DBMS (1)
        • HTML | CSS (3)
        • Git | GitHub (1)
        • JavaScript (5)
        • Node.js (5)
        • React (1)
        • 데이터 분석 (6)
        • Python Engineering (3)
      • 개념 정리 step2 (60)
        • Machine | Deep Learning (15)
        • 멀티모달(Multi-modal) (23)
        • 강화 학습 (10)
        • AI Agent (9)
        • 메디컬 이미지 (3)
      • 개인 공부 - 내가 공부하고 싶은 모든 것 (3)
        • 1. 인프라 (2)
        • 2. 자율주행 (0)
  • 블로그 메뉴

    • 홈
    • 태그
    • 방명록
  • 링크

    • Notion-포트폴리오
    • Github
  • 공지사항

    • 나의 핵심 가치
  • 인기 글

  • 태그

    RAG
    Vision
    알고리즘
    강화학습
    API
    구현
    Python
    자료구조
    Lora
    인공지능
    데이터분석
    OCR
    연구
    paddleocr
    github
    파인튜닝
    파이썬
    pandas
    Ollama
    프로젝트
    전처리
    논문 리뷰
    Agent
    학습
    공모전
    Ai
    transformer
    llm
    ViT
    자바스크립트
  • 최근 댓글

  • 최근 글

  • hELLO· Designed By정상우.v4.10.5
고니3000원
[개인 경진대회] Kaggle Playground Series S6E6 연구 (7): 193번째 프라이빗 일반화 후보 연구
상단으로

티스토리툴바