Engineering
작은 MoE 하나로 상용 한국어 OCR과 붙어봤다 — 학습은 아직 진행 중
활성 ~0.94B짜리 MoE OCR이 학습 8,000 step(전체 32,000 중) 시점에 Clova·Gemini·Upstage·MinerU·PaddleOCR과 5개 한국어 문서 트랙에서 정면 비교. 읽기순서는 이미 전체 1위, 추론은 4090 한 장으로 5트랙 8분(batch-1 대비 53배).
먼저 분명히 해두면 — 이 모델은 아직 학습 중이다. 전체 32,000 step 중 8,000 step 시점의 중간 체크포인트다. 그런데도 결과가 나쁘지 않아서, 중간 점검 겸 공개한다. 최종본은 더 좋아질 것이다.
작은 MoE 모델 하나(활성 파라미터 ~0.94B)가 Clova·Gemini·Upstage·MinerU·PaddleOCR 같은 상용 엔진과 같은 링에서 얼마나 버티는지, 5개 한국어 문서 트랙에서 정직하게 쟀다.
어떻게 측정했나
벤치마크는 OmniDocBench-KO Full eval. 한국어 문서를 5개 능력 트랙으로 나눠 채점한다.
| 트랙 | 내용 | 장수 |
|---|---|---|
| 일반 한국어 문서 | born-digital 일반 문서 | 100 |
| 표 기반 금융 | 표·폼 위주 금융 문서 | 60 |
| 슬라이드·강의안 | 발표자료 레이아웃 | 100 |
| 옛스캔(필기·옛공문) | 열화된 한국어 스캔 | 80 |
| 수능(인쇄+수식) | 수식 포함 시험지 | 100 |
두 축으로 잰다 (둘 다 0 = 완벽, 1 = 전부 틀림):
- 정확도(text) — 블록 매칭 후 각 블록의 정규화 편집거리(Levenshtein ÷ GT 길이). “글자를 얼마나 맞게 읽나”.
- 순서(order) — 읽기순서(reading order) 블록 편집거리. “어느 블록이 먼저인지 구조를 맞게 잡나”.
- 수능만 예외로 latexnorm CER(수식 정규화 후 문자 오류율).
그리고 mean과 median을 같이 본다. mean은 OmniDocBench 공식 지표(전 페이지 평균)이고, median은 표·복잡 레이아웃에서 터지는 폭발 페이지를 제외한 실제 중심 성능이다. 뒤에서 보겠지만, 이 둘의 차이가 많은 걸 말해준다.
공정성: 상용 엔진 5개를 우리 채점 파이프라인으로 재채점해 기존 측정치와 소수점까지 일치함을 확인했다(15개 전부 일치). 같은 자·같은 정답으로 잰 비교다. 우리 모델 출력(DocLang)만 동일 형식으로 변환해 조건을 맞췄다. 추론은 RTX 4090 한 장, vLLM.
전체 매트릭스
표기는 mean / median, 낮을수록 좋다. 보라색 행이 우리 MoE다.
| 엔진 | 정확도 text | 순서 order |
|---|---|---|
| Clova 🥇 | 0.019 / 0.003 | 0.039 / 0.000 |
| PaddleOCR | 0.065 / 0.005 | 0.027 / 0.000 |
| MinerU | 0.146 / 0.033 | 0.151 / 0.041 |
| 우리 MoE | 0.161 / 0.054 | 0.129 / 0.075 |
| Upstage | 0.171 / 0.023 | 0.156 / 0.000 |
| Gemini | 0.246 / 0.082 | 0.231 / 0.077 |
| 엔진 | 정확도 text | 순서 order |
|---|---|---|
| Clova | 0.296 / 0.260 | 0.433 / 0.467 |
| 우리 MoE | 0.340 / 0.233 | 0.218 / 0.174 🥇 |
| Gemini | 0.685 / 0.751 | 0.645 / 0.721 |
| Upstage | 0.733 / 0.780 | 0.643 / 0.758 |
| 엔진 | 정확도 text | 순서 order |
|---|---|---|
| Clova 🥇 | 0.080 / 0.000 | 0.085 / 0.000 |
| Upstage | 0.132 / 0.000 | 0.136 / 0.000 |
| Gemini | 0.138 / 0.000 | 0.136 / 0.000 |
| MinerU | 0.171 / 0.035 | 0.224 / 0.134 |
| 우리 MoE | 0.196 / 0.042 | 0.186 / 0.000 |
| PaddleOCR | 0.210 / 0.119 | 0.111 / 0.000 |
| 엔진 | 정확도 text | 순서 order |
|---|---|---|
| Clova 🥇 | 0.123 | 0.004 |
| 우리 MoE | 0.157 / 0.053 | 0.014 / 0.000 |
| Gemini | 0.260 | 0.136 |
| PaddleOCR | 0.290 | 0.062 |
| MinerU | 0.291 | 0.218 |
| Upstage | 0.373 | 0.282 |
| 엔진 | CER |
|---|---|
| MinerU 🥇 | 0.214 |
| Gemini | 0.251 |
| Upstage | 0.485 |
| 우리 MoE | 0.600 |
| Clova | 0.615 |
| PaddleOCR | 0.909 |
종합 성적
4개 본문 트랙 평균(MinerU·Paddle은 금융 결측이라 4트랙 비교에서 제외).
| 엔진 | text mean | text median | order mean | order median |
|---|---|---|---|---|
| Clova | 0.130 🥇 | 0.088 | 0.140 | 0.156 |
| 우리 MoE | 0.214 | 0.110 | 0.137 | 0.083 🥇 |
| 우리 dense(32k) | 0.246 | — | 0.169 | — |
| Gemini | 0.332 | 0.278 | 0.287 | 0.266 |
| Upstage | 0.352 | 0.268 | 0.304 | 0.253 |
- 읽기순서(order)는 우리 모델이 median 기준 전체 1위(0.083) — Clova(0.156)도 앞선다. 구조를 정확히 잡는 게 강점이다.
- 정확도(text)는 Clova가 최강(한국어 OCR 인식력). 우리는 그다음 그룹이되, 자사 dense를 능가한다.
표 채점의 함정 — median이 드러낸 것
금융에서 Gemini·Upstage는 median이 mean보다 더 높다(0.75, 0.78). 표를 markdown으로 출력하는데 정답은 plain 텍스트 블록이라, 거의 모든 페이지에서 매칭이 깨진다. OCR을 못해서가 아니라 표현 형식이 안 맞아서 점수가 터진다.
반대로 우리 모델만 median이 낮아진다(0.340 → 0.233). 표를 실제로 더 정확히 구조화한다는 뜻이다. 0.4 이상 점수는 “성능”이 아니라 “표 아티팩트”로 읽어야 한다 — 이게 이 트랙의 교훈이다.
추론 속도 — 4090 한 장으로 5트랙 8분
정확도만큼 중요한 게 속도다. Qwen2-VL 계열은 M-RoPE 위치 인코딩 때문에 일반적인 배치 추론이 출력을 오염시켜 batch-1을 강제당한다. 그대로 두면 한 장에 ~70초, 5트랙 460장이면 7.7시간이다.
여기에 세 가지를 얹었다 — vLLM의 ragged continuous batching, 발산 페이지 토큰 절단(무손실), 그리고 ngram speculative decoding(DocLang의 반복 구조를 draft로 제안, lossless라 출력 동일). 결과:
| 방식 | 5트랙 460장 | 처리량 |
|---|---|---|
| 단순 batch-1 | ~7.7시간 | ~1 img/min |
| vLLM + 2048 cap + ngram | ~8분 | ~55 img/min |
53배. 체크포인트가 2,000 step마다 쌓이는 학습 중에 매번 전 트랙을 빠르게 평가할 수 있다는 뜻이고, 온디바이스/엣지 배포에서도 의미 있는 throughput이다.
정리
활성 ~0.94B짜리 MoE가, 전체 학습의 4분의 1(8,000 / 32,000 step) 시점에 이미:
- 읽기순서는 상용 포함 median 기준 전체 1위,
- 금융·옛스캔 정확도는 자사 dense를 능가,
- 추론은 4090 한 장으로 5트랙 8분(53배).
남은 약점도 분명하다. **수식(수능)**은 아직 약하고(formula 데이터 추가 학습이 다음 레버), clean 텍스트 인식력에선 Clova가 여전히 벽이다.
다시 강조하면 — 이건 학습 중간 결과다. 남은 24,000 step이 이 숫자들을 어디까지 끌어올리는지는, 끝나고 다시 쓰겠다.
RAG Lab 구독
schift 만들면서 직접 굴린 RAG 실험 일지. 매주 새 실험이 올라옵니다.