minOS

자바의 정석 ch8-11~14 예외선언하기 ,finally블럭 본문

TIL/남궁성의 자바의 정석

자바의 정석 ch8-11~14 예외선언하기 ,finally블럭

minOE 2024. 9. 12. 11:24
728x90

ch8-11 메서드에 예외 선언하기

- 예외를 처리하는 방법 : try-catch문 (직접 처리), 예외 선언하기(자신을 호출한 곳에 예외 처리 떠넘기기)
- 메서드가 호출시 발생 가능한 예외를 호출하는 쪽에 알리는 것

구조
public void 메서드명() throws Exception1, Exception2, ..., ExceptionN {
    // 메서드 내용
}

예시
public class SimpleExceptionExample {
    public static void divide(int a, int b) throws ArithmeticException {
        System.out.println(a + " / " + b + " = " + (a / b));
    }

    public static void main(String[] args) {
        try {
            divide(10, 0);
        } catch (ArithmeticException e) {
            System.out.println("오류 발생: " + e.getMessage());
        }
    }
}​


divide 메서드는 ArithmeticException 발생시 메인 메서드 에서예외 처리를 한다.





- 자바에서 예외 명시


Unchecked Exceptions (RuntimeException 및 그 하위 클래스)
Checked Exceptions (Exception 클래스와 그 하위 클래스 중 RuntimeException을 제외한 모든 예외)

메서드 선언 시 throws 키워드 뒤에 명시해야 하는 예외는  Checked Exceptions이다. Unchecked Exceptions는 자율

예시
import java.io.FileReader;
import java.io.IOException;

public class CheckedExceptionExample {
    public static void readFile(String filename) throws IOException {
        FileReader reader = new FileReader(filename);
        // 파일 읽기 로직...
        reader.close();
    }

    public static void main(String[] args) {
        try {
            readFile("example.txt");
        } catch (IOException e) {
            System.out.println("파일 읽기 오류: " + e.getMessage());
        }
    }
}
  1. IOException은 Checked Exception이다.
  2. readFile 메서드는 IOException을 throws로 선언한다.
  3. 이 메서드를 호출하는 쪽에서는 반드시 이 예외를 처리해야 한다.(try-catch 또는 다시 throws).

반면, RuntimeException (예: ArithmeticException, NullPointerException)은 명시적으로 선언하지 않아도 된다.

이렇게 Checked Exception을 명시적으로 선언하게 함으로써, 자바는 개발자가 예외 상황을 인식하고 적절히 처리하도록 강제한다.



 

 

 8-12 메서드에 예외 선언하기  - 예제 1

public class Ex8_9 {
    public static void main(String[] args) throws Exception {
        method1();   // 같은 클르새내의  stati 멤버이므로 객체 생성 없이 직접 호출가능
    } // 메인 메서드끝


    static void method1() throws Exception{
        method2();
    } // method1 끝

    static void method2() throws Exception{
        throw new Exception();
    }  // method2 끝

}


호출 스택 그림

 

  • 메인 메서드가 예외를 처리하지 않고 JVM으로 전달합니다 (throws Exception).
  • 이로 인해 프로그램이 비정상적으로 종료됩니다.
  • JVM은 처리되지 않은 예외를 감지하고 기본 예외 처리기를 실행합니다.
  • 이 기본 예외 처리기는 예외의 스택 트레이스를 콘솔에 출력합니다.
이건 예외가 처리 된 것이 아니다. 처리하려면 try - catch 문이 필요하다.



 

 8-13 메서드에 예외 선언하기  - 예제 2

import java.io.File;

public class Ex8_10 {

    public static void main(String[] args) {
        try{
            File file = createFile(""); //예외발생
            System.out.println( file.getName()+ "파일이 성공적으로 생성되었습니다.");
        }catch (Exception e){
            System.out.println(e.getMessage()+" 다시 입력해 주시기 바랍니다.");
        }
    }

    static File createFile(String fileName) throws Exception{
        if(fileName ==null || fileName.equals(""))
            throw new Exception("파일 이름이 유효하지 않습니다");
        File f = new File(fileName);
        f.createNewFile();
        return f;
    }
    
}


출력 결과



import java.io.File;

public class Ex8_10 {

    public static void main(String[] args) {
        try{
            File file = createFile("바질토마토.txt"); //예외발생 x
            System.out.println( file.getName()+ "파일이 성공적으로 생성되었습니다.");
        }catch (Exception e){
            System.out.println(e.getMessage()+" 다시 입력해 주시기 바랍니다.");
        }
    }

    static File createFile(String fileName) throws Exception{
        if(fileName ==null || fileName.equals(""))
            throw new Exception("파일 이름이 유효하지 않습니다");
        File f = new File(fileName);
        f.createNewFile();
        return f;
    }

}

 



예외 선언하지 않고 메서드 안에서 예외 처리 하기

import java.io.File;
import java.io.IOException;

public class Ex8_10 {

    public static void main(String[] args) {
        File file = createFile("");
        if (file != null) {
            System.out.println(file.getName() + " 파일이 성공적으로 생성되었습니다.");
        }
    }

    static File createFile(String fileName) {
        File f = null;
        try {
            if (fileName == null || fileName.equals(""))
                throw new IllegalArgumentException("파일 이름이 유효하지 않습니다");
            f = new File(fileName);
            f.createNewFile();
        } catch (IllegalArgumentException e) {
            System.out.println(e.getMessage() + " 다시 입력해 주시기 바랍니다.");
        } catch (IOException e) {
            System.out.println("파일 생성 중 오류가 발생했습니다: " + e.getMessage());
        }
        return f;
    }
}

 

 

 8-14 finally 블럭

- 예외 발생 여부와 관계없이 수행되어야 하는 코드를 넣는다
try {
    // 예외가 발생할 수 있는 코드
} catch (예외타입1 e) {
    // 예외타입1에 대한 처리
} catch (예외타입2 e) {
    // 예외타입2에 대한 처리
} finally {
    // 예외 발생 여부와 관계없이 항상 실행되는 코드
}​

finally 블록은 리소스 정리나 로그 기록 등 항상 실행되어야 하는 코드에 사용딘다. 예외가 발생하든 하지 않든, 심지어 try 블록 내에서 return문이 실행되더라도 finally 블록은 반드시 실행된다.

 

728x90