passion and relax

[JAVA] 11. 위험한 행동 (예외 처리) 본문

프로그래밍

[JAVA] 11. 위험한 행동 (예외 처리)

Grab Java 2024. 5. 27. 19:48

Java의 Exception handling (예외처리)

예외적인 상황을 처리하는 깔끔하고 부담없는 방법
"호출할 메소드가 예외를 발생시킬 수 있다면 , 그 예외가 발생했을 때 처리할 방법을 정의해둔다"
호출할 메소드가 어떤 예외를 발생할 수 있는가를 어찌 알수 있는가?
. document의 해당 메소드에 "Throws"를 보면 알 수 있다.

try, catch, finally

실행 중에 문제가 생기면, 메소드에서 Exception 유형의 객체인 예외를 던진다.
실패하든, 성공하든, finally는 실행된다.
try 또는 catch 안에 return이 있어도, finally는 실행 후에 return 된다.
catch에 쓸 것이 없으면, 적어도 e.printStackTrace() 라도 찍어라.
위험한 메소드에서 throws한 예외를 catch 해야 한다. 다른 예외를 catch 해봐야 소용없다.
예외가 상속된 예외라면, 그 상위의 예외를 catch 해도 된다.
여~엉 귀찮으면 예외의 최상위인 Exception을 1번만 catch 해라.
try 없는 catch나 fianlly는 없다.
try를 썼으면, catch나 finally 둘 중 어느 하나만 있으면 된다.
단 try - finally가 되면, 예외처리가 제대로 된 것이 아니기에, throws문을 선언해야 한다.(예외회피)
try와 catch 사이에 다른 코드가 오면 안된다.

 


Java Sound API

MIDI
. 악기 디지털 인터페이스 (Musical Instruments Digital Interface)
. 서로 다른 종류의 전자음악기기 끼리 의사소통을 하기 위한 표준 프로토콜
. 소리는 없고, 악기를 다루는 방법이 들어 있다.
Sampled

 


Sequencer 클래스

위에 설명한 예외 처리를 추가하였다.

import javax.sound.midi.*;

public class MusicTest1 {
    public void play() {
        try {
            Sequencer sequencer = MidiSystem.getSequencer();
            sout("succcess");
        } catch (MidiUnavailableException ex) {
            sout("failure");
        }
    }

    public static void main (String[] args) {
        MusicTest1 mt = new MusicTest1();
        mt.play();
    }
}

 


throws : 하나의 예외 던지고 받기

위험한 메소드를 만들 때, 예외를 던질 수 있다.

public void takeRisk() throws BadException {
    if (abandonAllHope) {
        throw new BadException();
    }
}

public void crossFingers() {
    try {
        anObject.takeRisk();
    } catch (BadException ex) {
        sout("um..");
        ex.printStackTrace();
    }
}

throws : 여러 예외 던지고 받기

두개 이상 던질 수도 있다. 물론 두개를 다 받아야(catch 해야) 한다.

public class Laundry {
    public void doLaundry() throws PantsException, LingerieException {
        //두 예외를 던지는 코드
    }
}

public class Foo {
    public void go() {
        Laundry laundry = new Laundry();
        try {
            laundry.doLaundry();
        } catch (PantsException pex) {
            //복구 코드
        } catch (LingerieException lex) {
            //복구 코드
        }
    }
}

 


throws : 상속된 예외 던지고 받기

상위의 예외라면, 여러 하위의 예외를 하나의 상위 예외로 받을 수도 있다.
    하지만 세세한 처리는 포기하는 것. 세세하려면, 하위를 모두 catch 해야 한다.
상속된 예외에 있어, 하위부터 catch 해야 한다. 상위부터 하면 그 하위는 호출 되지 않는다.
최상위인 Exception을 catch 하면, 하나만 써도 된다.
예외처리를 피할 때에도 사용된다. (main()에서 까지도 회피할 수도 있다)
public class Laundry {
    public void doLaundry() throws PantsException, LingerieException {
        //두 예외를 던지는 코드
    }
}

public class Foo  throws ReallyBadException {
    public void go() {
        Laundry laundry = new Laundry();
        laundry.doLaundry();
    }
}

 


컴파일러가 예외와 관련하여 하는 일

개발자가 예외를 만들어 던지고 있다면..
. 메소드 선언부에 throws를 선언 했는지 확인한다. 안되어 있으면 에러
개발자가 예외를 던지고 있는 함수를 호출하고 있다면..
. throws를 선언해서 예외를 전가하고 있는지 확인. 전가하고 있으면 OK
. 전가하지 않으면서 try catch 문도 없다면 에러
RuntimeException은 처리하지 못한다.
. 미리 예측해서 하던가.. 발생할 때 마다 해당 예외를 추가하는 것이 바람직.