Programming

Checked vs Unchecked Exception에 대해서 설명해주세요

컴파일러가 강제하는 Checked Exception과 런타임에 발생하는 Unchecked Exception의 차이, 언제 무엇을 써야 하는지, Spring Boot의 관행까지 인터랙티브 시각화로 완전 정복합니다.

2026년 3월 16일 · 약 10분 읽기

Q. "Java의 Checked Exception과 Unchecked Exception의 차이를 설명하고, 실무에서 어떻게 선택하는지 말씀해주세요."

예상 꼬리질문

답변 가이드

"Java 예외는 Checked(컴파일러가 처리를 강제)와 Unchecked(런타임 발생, 강제 없음) 두 종류로 나뉩니다. RuntimeException을 상속하면 Unchecked, 그렇지 않으면 Checked입니다."

"Checked Exception을 남용하면 모든 레이어에 throws가 오염됩니다. 판단 기준은 '호출자가 이 예외를 회복할 수 있는가'입니다. 회복 가능하면 Checked, 불가능하면 Unchecked를 사용합니다."

"Spring Boot에서는 Unchecked RuntimeException + @RestControllerAdvice로 전역 처리하는 것이 표준 패턴입니다. Spring Data JPA도 내부 SQLException을 DataAccessException(Unchecked)으로 변환합니다."

IOException은 왜 try-catch가 필수인데, NullPointerException은 catch 안 해도 컴파일이 될까요? 두 예외의 차이가 바로 Checked와 Unchecked입니다.

어떤 예외를 써야 할지 고민했다면, 이 아티클이 명확한 기준을 제시합니다. 계층 구조부터 판단 기준, Spring Boot 실전 패턴까지 직접 만져볼 수 있는 시각화로 체험합니다.


1. Java 예외 계층 구조

꼬리질문: "Java 예외 계층 구조에서 Checked와 Unchecked를 구분하는 기준이 뭔가요?"

Java의 모든 예외는 Throwable을 최상위로 하는 계층 구조를 갖습니다. Error는 JVM 수준의 복구 불가능한 오류이고, Exception은 프로그램이 처리할 수 있는 예외입니다.

핵심 규칙은 단순합니다: RuntimeException을 상속하면 Unchecked, 그렇지 않으면 Checked입니다. 컴파일러는 이 계층을 기준으로 처리 강제 여부를 판단합니다.

아래에서 각 예외 클래스의 위치와 분류를 직접 확인해 보세요.

노드를 클릭하면 해당 클래스의 설명을 확인할 수 있습니다

Checked Exception
Unchecked Exception
Root

2. 핵심 차이 — Checked vs Unchecked

꼬리질문: "Checked Exception을 남용하면 어떤 문제가 생기나요?"

Checked Exception을 던지는 메서드는 반드시 throws IOException처럼 시그니처에 선언해야 하고, 호출자는 반드시 try-catch로 처리하거나 다시 throws로 위임해야 합니다.

Checked를 남용하면 모든 메서드에 throws가 붙어 코드가 오염됩니다. 반면 Unchecked만 쓰면 예외 처리 누락이 런타임까지 발견되지 않습니다. 두 방식의 실질적 차이를 비교해 보세요.

두 방식의 코드 작성 차이를 직접 비교해 보세요.

Checked Exception

Exception 상속

🔍컴파일 타임에 검사됨
📝throws 선언 필수
🛡️try-catch 처리 강제
🌐외부 환경 오류 (파일, DB, 네트워크)

대표 예시

IOExceptionSQLExceptionParseException
Unchecked Exception

RuntimeException / Error 상속

런타임에 발생
✂️throws 선언 불필요
🎯try-catch 선택 사항
🐛프로그래밍 버그 (null, 잘못된 인수)

대표 예시

NullPointerExceptionIllegalArgumentException

3. 언제 무엇을 써야 하나 — 판단 기준

꼬리질문: "언제 Checked를 쓰고 언제 Unchecked를 써야 하나요?"

Oracle의 공식 가이드라인은 명확합니다: "호출자가 합리적으로 회복할 수 있다면 Checked, 그렇지 않다면 Unchecked." 파일이 없을 때 기본 파일을 사용하거나 사용자에게 알릴 수 있다면 Checked(IOException)가 적절합니다.

Joshua Bloch는 Effective Java에서 "불필요한 Checked Exception 사용을 피하라"고 권고합니다. C#, Kotlin은 처음부터 Checked Exception을 채택하지 않았으며, Spring·Hibernate는 내부 Checked Exception을 Unchecked로 래핑하는 방향으로 발전했습니다.

판단 플로우를 따라가며 어떤 예외를 선택해야 하는지 확인해 보세요.

질문 1

호출자가 이 예외 상황에서 합리적으로 회복할 수 있는가?

4. Spring Boot 실전 패턴

꼬리질문: "Spring Boot에서는 예외를 어떻게 처리하는 게 표준인가요?"

Spring Boot에서는 Unchecked Exception + @ControllerAdvice 패턴이 표준입니다. RuntimeException을 상속하는 커스텀 예외를 던지고, @RestControllerAdvice에서 전역으로 처리합니다.

Spring Data JPA는 내부적으로 JDBC의 SQLException(Checked)을 DataAccessException(Unchecked)으로 변환합니다. 덕분에 Repository 레이어에서 DB 예외를 처리하면서도 서비스 코드가 깔끔하게 유지됩니다.

예외가 발생했을 때 Spring 내부의 흐름을 직접 따라가 보세요.

레이어를 클릭하면 상세 설명을 확인할 수 있습니다

예외 발생 중
전파 완료
최종 처리

Database

오류 발생 (데이터 없음, 연결 실패 등)

예외 전파

@Repository (Spring Data JPA)

SQLException → DataAccessException 자동 변환

예외 전파

@Service

throw new UserNotFoundException(id)

예외 전파

@RestController

예외를 잡지 않고 전파

예외 전파

@RestControllerAdvice

@ExceptionHandler → HTTP 404 응답 반환


면접 체크리스트

이 항목들을 자신 있게 설명할 수 있다면 예외 처리 질문은 준비 완료입니다.

  • - 계층 구조: RuntimeException 상속 여부가 Checked/Unchecked를 결정
  • - Checked Exception: Exception 상속 / 컴파일 강제 / 회복 가능한 외부 오류에 사용
  • - Unchecked Exception: RuntimeException 상속 / 강제 없음 / 프로그래밍 버그 또는 복구 불가 상황
  • - 판단 기준: "호출자가 회복할 수 있는가?" YES → Checked, NO → Unchecked
  • - Spring Boot 표준: Unchecked RuntimeException + @RestControllerAdvice 전역 처리

참고 자료


의견을 들려주세요

서비스 개선에 큰 도움이 됩니다. 익명으로 자유롭게 남겨주세요.

0 / 1000