모델 설계 범위
모델은 이미지나 텍스트를 embedding vector로 바꾼다. 학습의 목표는 같은 랜드마크의 이미지와 문장이 embedding 공간에서 가까워지고, 다른 랜드마크나 hard negative는 충분히 멀어지도록 만드는 것이다.
image input → image_embedding
text input → text_embedding
ML Background · 2026-05-20
모델 학습을 시작하기 전에 무엇을 먼저 정해야 하는지 정리한 문서다. 핵심은 Loss부터 고르는 것이 아니라, 문제 정의와 평가 기준을 먼저 고정한 뒤 그 목표를 달성하도록 모델, 데이터셋, Loss를 설계하는 것이다.
사용자가 정리한 순서인 “무엇을 학습할 것인가 → 목표 → 학습 방식 → Loss → 데이터셋 → 평가”는 큰 방향에서 맞다. 다만 실전에서는 데이터셋 구조와 평가 방식도 학습 전에 먼저 설계해야 한다. 그래야 나중에 모델 점수가 잘 나왔을 때 그것이 진짜 개선인지, 단순히 train set에 익숙해진 것인지 구분할 수 있다.
또 하나 중요한 구분이 있다. MobileCLIP2 계열 같은 embedding 모델의 직접 출력은 Top-3나 matched/out_of_scope가 아니라 image/text embedding이다. Top-3 정렬, confidence, decision status는 모델 다음 단계인 검색 서비스와 앱 정책 레이어가 만든다.
Sprint 2 설계에서 모델 문제와 앱 문제를 섞으면 원인 분석이 어려워진다. 예를 들어 광화문이 낮은 점수로 나왔을 때, embedding 공간 자체가 나쁜 것인지, prototype 생성 방식이 나쁜 것인지, threshold 정책이 너무 엄격한 것인지 분리해서 봐야 한다.
모델은 이미지나 텍스트를 embedding vector로 바꾼다. 학습의 목표는 같은 랜드마크의 이미지와 문장이 embedding 공간에서 가까워지고, 다른 랜드마크나 hard negative는 충분히 멀어지도록 만드는 것이다.
image input → image_embedding
text input → text_embedding
검색 서비스는 모델이 만든 embedding을 landmark prototype, text catalog embedding과 비교한다. 그 결과 모든 후보의 similarity score list를 만들고, 이를 정렬해 Top-K 후보를 만든다.
embedding
→ cosine similarity with candidates
→ score list
→ ranking
앱 정책은 score와 margin을 해석해 matched, ambiguous, out_of_scope, low_quality를 결정한다. UI는 그 결정을 사용자가 이해할 수 있는 문구와 화면으로 보여준다.
score + margin
→ decision_status
→ user-facing result
먼저 제품 관점의 문제를 정한다. Landmark Assistant에서는 이미지 입력으로 특정 랜드마크를 인식하고, 자연어 입력으로 관련 랜드마크를 찾으며, 애매하거나 지원 범위 밖인 입력은 확정하지 않는 것이 목표다.
좁은 의미의 모델 출력은 image_embedding과 text_embedding이다.
따라서 모델 설계에서는 “정답 class를 바로 내는가?”보다 “어떤 입력들이 embedding 공간에서
가까워져야 하고, 어떤 입력들이 멀어져야 하는가?”를 먼저 정한다.
목표를 숫자와 기준으로 바꾼다. 예를 들어 Top-1 accuracy, Top-3 accuracy, 광화문과 경복궁 근정문 같은 hard case 정확도, 자연어 검색 Recall@1/3, out-of-scope 거절률, 모바일 latency, 모델 크기를 정한다. 이때 Top-3와 decision status는 모델 raw output이 아니라 검색/정책 레이어의 평가 항목이라는 점을 구분한다.
이미지와 landmark_id만으로는 부족할 수 있다. Multi-task 학습을 고려한다면
이미지별 한/영 caption, 랜드마크별 text catalog, hard negative 관계,
train/validation/test split, non-confirmed 또는 out-of-scope 샘플 정책까지 같이 정해야 한다.
MobileCLIP2-S3/S4를 그대로 feature extractor로 쓸지, image encoder 일부를 fine-tuning할지, text encoder도 학습할지, classifier head를 붙일지, contrastive learning을 같이 할지 정한다.
Loss는 모델에게 “좋은 결과와 나쁜 결과를 숫자로 알려주는 기준”이다. 특정 랜드마크 이름을 맞히려면 classification loss가 필요하고, 이미지와 설명 문장을 같은 의미 공간에 두려면 image-text contrastive loss가 필요하다. 비슷한 건물을 더 잘 구분하려면 hard negative 또는 supervised contrastive loss를 추가할 수 있다.
batch size, learning rate, epoch, augmentation, freeze/unfreeze 범위, loss weight를 정한다. 예를 들어 multi-task에서는 아래처럼 총 Loss를 구성할 수 있다.
total_loss =
classification_loss
+ 0.2 * image_text_contrastive_loss
+ 0.1 * hard_negative_loss
train score는 학습이 진행되는지 확인하는 값이고, validation score는 모델 선택과 threshold 조정에 사용한다. test score는 마지막 보고용으로 잠가두어야 한다. test set을 보면서 계속 튜닝하면 실제 성능을 과대평가하게 된다.
모델이 좋아 보여도 앱에 실을 수 없으면 Sprint 목표를 달성했다고 보기 어렵다. ONNX/TFLite export 가능 여부, 모바일 latency, Top-3 결과 일치성, 모델 크기, 앱에서 실제로 사용할 수 있는 artifact 구조를 확인한다.
우리 프로젝트에서 “나쁜 결과”는 단순히 정답을 틀리는 것만이 아니다. 예를 들어 광화문 이미지가 청와대와 가까워지는 것, 근정문 이미지가 광화문으로 과하게 끌리는 것, “돌담 있는 공원”이라는 질의가 낙산공원이 아니라 보현산신각으로 가는 것, 지원 범위 밖 이미지인데 높은 confidence로 특정 랜드마크를 확정하는 것도 모두 나쁜 결과다.
따라서 Sprint 2 모델 설계에서는 단순 Top-1 accuracy만 보지 말고, hard case margin, Top-3 후보 품질, 자연어 검색 품질, out-of-scope 거절, 모바일 실행 가능성을 함께 봐야 한다.
다만 이 항목들은 서로 다른 레이어에 걸쳐 있다. hard case margin과 자연어 검색 품질은 embedding space의 영향을 크게 받지만, out-of-scope 판단과 ambiguous 문구는 threshold와 UI 정책의 영향도 크다. 그래서 평가 결과를 기록할 때는 모델 문제, 검색 서비스 문제, 앱 정책 문제를 나눠 적는 것이 좋다.
Loss는 출발점이 아니라 도구다. 먼저 “무엇을 잘해야 하는지”와 “잘했다는 것을 어떻게 측정할지”를 정하고, 그다음에 그 목표를 모델에게 가르치기 위한 Loss를 선택한다.
문제 정의
→ 모델이 만들어야 할 embedding 관계 정의
→ 목표 지표 정의
→ 데이터셋 구조와 split 설계
→ 모델 구조 선택
→ 학습 방식 선택
→ Loss 구성
→ 평가, 검색 정책, 배포 검증