예외 처리 문법

예외 처리 문법은 프로그래밍 언어에서 프로그램 실행 중 발생할 수 있는 예기치 않은 오류나 특수한 상황(예외)을 감지하고, 이를 적절하게 처리하기 위해 정의된 특정 구문 및 구조를 의미한다. 이는 프로그램의 안정성과 견고성을 높이고, 예외 상황으로 인한 비정상적인 종료를 방지하여 사용자 경험을 개선하는 데 필수적인 요소이다.


목적 및 필요성

예외 처리 문법의 주된 목적은 다음과 같다.

  • 프로그램 안정성 확보: 예상치 못한 오류 발생 시 프로그램이 강제 종료되는 것을 막고, 복구 로직을 수행하거나 제어된 방식으로 종료할 수 있게 한다.
  • 오류 처리 로직 분리: 일반적인 프로그램 흐름과 오류 처리 로직을 분리하여 코드의 가독성과 유지보수성을 향상시킨다.
  • 자원 해제 보장: 파일 핸들, 네트워크 연결 등 할당된 자원이 예외 발생 여부와 관계없이 항상 해제되도록 보장한다.

주요 구성 요소

대부분의 현대 프로그래밍 언어에서 예외 처리 문법은 다음과 같은 핵심 구성 요소를 포함한다.

  • try 블록 (시도 블록): 예외 발생 가능성이 있는 코드를 포함하는 부분이다. 이 블록 내에서 예외가 발생하면, 해당 예외를 처리하기 위한 과정이 시작된다.
  • catch 또는 except 블록 (포착/예외 블록): try 블록에서 특정 유형의 예외가 발생했을 때 실행되는 코드이다. 각 catch 또는 except 블록은 특정 예외 유형을 처리하도록 정의될 수 있으며, 해당 예외에 대한 복구 로직이나 오류 메시지 출력 등을 담당한다.
  • finally 또는 ensure 블록 (최종 블록): 예외 발생 여부와 관계없이 try 블록이 종료된 후 항상 실행되도록 보장하는 코드이다. 주로 자원 해제(파일 닫기, 네트워크 연결 끊기 등)와 같은 필수적인 정리 작업을 수행하는 데 사용된다.

작동 방식

일반적으로 예외 처리 문법은 다음과 같은 흐름으로 작동한다.

  1. 프로그램은 try 블록 내의 코드를 실행한다.
  2. try 블록 내에서 예외가 발생하면, 현재 실행 흐름이 중단되고 해당 예외를 처리할 수 있는 catch 또는 except 블록을 찾는다.
  3. 적합한 catch/except 블록을 찾으면 해당 블록의 코드를 실행하여 예외를 처리한다.
  4. 예외 발생 여부와 관계없이, finally/ensure 블록이 있다면 항상 실행된다.
  5. 적합한 catch/except 블록을 찾지 못하면, 예외는 상위 호출 스택으로 전파되며, 최종적으로 처리되지 않을 경우 프로그램이 종료될 수 있다.

예시

대부분의 현대 프로그래밍 언어는 각기 다른 형태의 예외 처리 문법을 제공한다.

  • Java, C#, C++: try-catch-finally 구문을 사용한다.
    try {
        // 예외가 발생할 수 있는 코드
        int result = 10 / 0; // ArithmeticException 발생
    } catch (ArithmeticException e) {
        // ArithmeticException 처리 로직
        System.err.println("0으로 나눌 수 없습니다: " + e.getMessage());
    } finally {
        // 항상 실행되는 코드 (자원 해제 등)
        System.out.println("예외 처리 구문 종료.");
    }
    
  • Python: try-except-finally 구문을 사용한다.
    try:
        # 예외가 발생할 수 있는 코드
        result = 10 / 0 # ZeroDivisionError 발생
    except ZeroDivisionError as e:
        # ZeroDivisionError 처리 로직
        print(f"0으로 나눌 수 없습니다: {e}")
    finally:
        # 항상 실행되는 코드
        print("예외 처리 구문 종료.")
    
  • Ruby: begin-rescue-ensure 구문을 사용한다.

장점

  • 프로그램 강건성: 예측 불가능한 상황에서도 프로그램이 안정적으로 동작하게 한다.
  • 코드 분리: 정상 로직과 오류 처리 로직을 명확히 구분하여 코드의 구조를 깔끔하게 유지한다.
  • 유지보수 용이성: 오류 발생 시 처리 로직을 한 곳에 모아 관리함으로써 유지보수를 용이하게 한다.

단점 및 고려 사항

  • 성능 오버헤드: 예외 처리는 일반적인 조건 검사에 비해 상대적으로 성능 오버헤드가 발생할 수 있다.
  • 남용 지양: 예외는 예외적인 상황에만 사용해야 하며, 일반적인 프로그램 흐름 제어에 남용해서는 안 된다. 잘못된 예외 처리 방식은 오히려 코드의 가독성을 해치고 디버깅을 어렵게 만들 수 있다.

같이 보기

  • 예외 처리
  • 오류 처리
  • 런타임 오류
  • 디버깅
둘러보기

더 찾아볼 만한 주제