지난 글까지 추론 모델을 어떻게 쓰는지를 다뤘다면, 이번에는 그 앞의 결정을 정리한다. 쓸 것인가 말 것인가. 이 판단이 흐리면 뒤의 모든 튜닝이 헛돈다. 예산을 아무리 잘 나눠도 애초에 추론이 필요 없는 작업에 붙어 있으면 비용만 나가고, 반대로 필요한 자리에 안 붙어 있으면 정답률이 안 오른다. 그리고 이 결정은 취향이 아니라 세 개의 측정 가능한 값으로 내릴 수 있다.
세 가지 질문
순서가 중요하다. 위에서부터 묻고, 하나라도 아니오가 나오면 거기서 멈춘다.
질문 1 — 정답을 기계적으로 검증할 수 있나
추론 모델의 강점은 답을 내기 전에 스스로 검토하는 데 있다. 그 검토가 의미를 가지려면 맞고 틀림이 있어야 한다. 계산 결과, 코드의 테스트 통과 여부, 스키마 충족 여부, 논리적 일관성처럼 판정이 가능한 것들이다.
반대로 "이 문장이 더 자연스러운가", "이 요약이 적절한가" 같은 질문에는 검토가 붙을 자리가 없다. 모델이 사고 구간에서 대안을 비교해 봐야 그 비교의 기준 자체가 취향이라 수렴하지 않는다. 이런 작업에서 추론 모델을 켜면 답변이 조심스러워지고 길어지기만 한다.
같은 이유로, 정답이 없으면 증류도 자체 평가 셋도 못 만든다. 개선 경로가 통째로 막힌다는 뜻이다.
이 질문에 아니오면 일반 모델에 루브릭 기반 평가를 붙이는 쪽이 맞다.
질문 2 — 한 번에 못 맞히는 비율이 높나
정답 판정이 되면 이제 실제로 얼마나 틀리는지를 잰다. 일반 모델에 CoT 프롬프팅까지 붙여 놓고 100건을 돌려 정답률을 본다.
- 90% 이상 맞는다 — 추론 모델을 붙일 이유가 없다. 남은 10%를 위해 전체 트래픽 비용을 몇 배로 올리는 셈이다. 그 10%는 사람 검수나 재시도로 처리하는 쪽이 싸다.
- 60~90% — 판단이 갈리는 구간이다. 3번 질문으로 넘어간다.
- 60% 미만 — 추론 모델이 값을 할 가능성이 크다. 다만 실패 원인을 먼저 읽어야 한다. 아래에서 다시 다룬다.
여기서 자주 빠지는 함정은 정답률을 재지 않고 "어려운 작업이니까"라는 인상으로 결정하는 것이다. 사람에게 어려운 것과 모델에게 어려운 것은 자주 다르다. 사람이 보기에 복잡한 규칙 적용을 모델은 잘 하고, 사람이 보기에 사소한 단위 변환에서 모델이 틀린다.
질문 3 — 지연 5초 이상을 감당할 수 있나
앞의 둘을 통과해도 지연 예산이 없으면 못 쓴다. 사고 구간은 통째로 침묵이고, 그 길이는 예산에 비례한다. 실시간 대화나 타이핑 중 자동 완성 같은 자리에는 들어갈 수 없다.
여기서 아니오라면 대안이 있다. 일반 모델 병렬 샘플링이다. 같은 질문을 N번 동시에 던져 다수결하거나 검증기로 고른다. 지연은 1회 호출과 거의 같고 비용만 N배다. 지연 예산이 빠듯하고 비용에 여유가 있을 때 이쪽이 정답이다.
셋을 모두 통과하면 추론 모델을 켠다. 단, 전체 트래픽이 아니라 등급을 나눠서다.
실패 원인을 먼저 읽는다
정답률이 낮다고 바로 추론 모델로 가면 안 되는 이유가 있다. 실패에는 종류가 있고, 추론 모델이 고쳐 주는 종류는 하나뿐이다.
| 실패 유형 | 증상 | 맞는 처방 |
|---|---|---|
| 지식 부족 | 없는 사실을 만들어 냄 | RAG, 컨텍스트 보강 |
| 지시 오독 | 요구사항 일부를 빠뜨림 | 프롬프트 분해, 예시 추가 |
| 형식 위반 | 파싱 실패, 스키마 불일치 | 구조화 출력, 검증 후 재시도 |
| 계산 실수 | 중간 값을 틀림 | 도구 호출, 코드 실행 |
| 접근 오류 | 처음부터 잘못된 방향 | 추론 모델 |
마지막 줄만이 추론 모델의 영역이다. 앞의 넷에 추론 모델을 붙이면 틀린 답을 더 자신 있게 낸다. 특히 지식 부족에 추론 모델을 붙이는 것이 위험하다. 사고 구간에서 없는 사실을 근거로 정교한 논증을 만들어 내고, 그 결과가 매우 그럴듯해 보인다.
실패 사례를 30건만 읽어 보면 어느 줄에 속하는지 대체로 갈린다. 이 30분이 몇 달치 API 비용을 좌우한다.
등급을 나눠 붙인다
"쓴다/안 쓴다"의 이분법으로 결정하지 않는 것이 실무의 기본형이다. 같은 서비스 안에서도 요청마다 필요한 사고량이 다르므로 등급을 나눈다.
from dataclasses import dataclass
@dataclass(frozen=True)
class Tier:
model: str
budget: int | None # None이면 사고 비활성
max_tokens: int
TIERS = {
"trivial": Tier("claude-haiku-4-5-20251001", None, 1024),
"normal": Tier("claude-sonnet-5", None, 2048),
"hard": Tier("claude-opus-5", 3000, 8000),
}
def pick(req) -> Tier:
# 값싼 신호부터 본다. 분류 모델을 부르는 건 마지막 수단.
if req.kind in ("greeting", "lookup", "format"):
return TIERS["trivial"]
if req.kind == "solve" and req.difficulty_hint >= 2:
return TIERS["hard"]
if len(req.body) > 4000 or req.has_constraints:
return TIERS["hard"]
return TIERS["normal"]
라우팅 규칙은 처음에 단순하게 시작한다. 요청 종류와 길이 두 개면 대개 충분하고, 트래픽 로그가 쌓이면 다듬는다. 여기에 분류 모델을 먼저 붙이면 그 호출의 지연과 비용이 절감분을 잡아먹는 경우가 많다.
그리고 승급 경로를 하나 둔다. 낮은 등급에서 시작해 실패(검증 불통과, 예산 소진, 형식 오류)했을 때만 위 등급으로 다시 던진다. 대부분의 트래픽이 낮은 등급에서 끝나므로 평균 비용이 크게 준다.
추론 모델을 붙이면 안 되는 자리
명확히 손해인 곳들을 목록으로 정리해 둔다.
- 분류·라우팅 — 짧은 판단에 사고 구간이 붙으면 지연이 지배적이 된다
- 정보 추출 — 원문에 있는 것을 뽑는 작업. 사고가 원문에 없는 해석을 더한다
- 번역·문체 변환 — 검증 기준이 취향이라 검토가 수렴하지 않는다
- 요약 — 위와 같은 이유. 게다가 길어지는 경향이 요약의 목적과 충돌한다
- 스트리밍이 UX의 핵심인 자리 — 침묵 구간이 경험을 망친다
- 초당 수백 건이 들어오는 경로 — 처리량 관점에서 감당이 안 된다
이 목록에 들어가는 작업에 추론 모델이 붙어 있으면 그것만 떼어 내도 비용의 상당 부분이 사라진다. 비용 절감 순서에서 1번이 압도적으로 효과가 컸던 이유다.
결정을 문서로 남긴다
마지막으로 실무에서 가장 자주 빠지는 것을 짚는다. 이 판단은 한 번 하고 끝이 아니다. 모델이 바뀌고 트래픽이 바뀌면 답도 바뀐다. 반년 뒤 일반 모델이 지금 추론 모델 수준의 정답률을 내면 등급 구성을 다시 짜야 한다.
그래서 결정할 때 근거를 같이 남긴다. 어떤 문항 100건으로 쟀는지, 각 경로의 정답률·비용·p95 지연이 얼마였는지, 어떤 실패 유형이 지배적이었는지. 이 기록이 있으면 다음 재평가가 하루면 끝나고, 없으면 처음부터 다시 한다.
세 질문은 모두 숫자로 답할 수 있다. 감으로 답하고 싶어지는 순간이 오면 그건 아직 재 보지 않았다는 신호다.
지난 글: 추론 모델의 비용과 지연을 다루는 법
읽어주셔서 감사합니다. 😊

