자바의 예외 처리에 대해 학습하세요.
- 자바에서 예외 처리 방법 (try, catch, throw, throws, finally)
- 자바가 제공하는 예외 계층 구조
- Exception과 Error의 차이는?
- RuntimeException과 RE가 아닌 것의 차이는?
- 커스텀한 예외 만드는 방법
try { // 예외 발생 가능성이 있는 코드 블록
...
// try에서 예외가 발생하면 catch로 이동한다.
// throw 키워드를 통해 직접 예외 인스턴스를 생성하는 경우
if () {
throw new Exception("..."); - (1)
}
if () {
throw new ChildException("..."); - (2) // extends Exception
}
if () {
throw new ChildChildException("..."); - (3) // extends ChildException
}
// 예외가 발생하면 try블록의 예외 아래 코드들은 실행되지 않고 무시된다. 그러므로 try블록의 return도 실행되지 않는다.
...
return ...
// try블록에서 다양한 예외를 처리해주기 위해 그에 따라 여러 catch블록이 존재
// 그러므로 발생한 예외에 따라 어떤 catch블록가 처리해주는지 확인(catch블록의 Exception의 상속구조 확인)
} catch (ChildChildException e) { - (3)
return ...;
} catch (ChildException e) { - (2)
return ...;
} catch (Exception e) { - (1)
return ...;
// java7 이후 catch블록에 하나 이상의 Exception(multi-catch) 사용가능, 사용하는 Exception들 상속관계 X
} catch (ExceptionA | ExceptionB e) {
return ...;
} catch (ChildException | Exception e) { - 틀린 문법
return ...;
} finally { // 예외 발생 여부와 관계없이 무조건 발생하는 블록
// try와 catch가 실행된 후에도 작동, 즉 try와 catch에서 return이 호출되어도 finally는 호출된다.
// 파일 입출력 이후 close을 해줄 때 많이 사용(resource leak를 방지하기 위한)
// java7에서 try-with-resources로 파일 close를 finally블록 사용하지 않아도 자원 쉽게 해제 가능
}
try
catch
finally
try-with-resource (JAVA 7 이후)
try/catch
를 통해 예외처리를 해야 하지만 try-with-resource
을 사용하면 이 경우 package java.lang;
public interface AutoCloseable {
void close() throws Exception;
}
package java.io;
import java.io.IOException;
public interface Closeable extends AutoCloseable {
public void close() throws IOException;
}
class Resource1 implements AutoCloseable {
...
@Override
void close() throws Exception {
// finally블록에서 수행할 작업
}
}
try (Resource1 r1 = new Resource1();
Resource2 r2 = new Resource2()) {
use(r1);
use(r2);
} catch (Exception e) {
...
}
try-with-resource의 동작 순서 - 확실하지 않음
try (Resource resource = new Resource()) {
// - (1) : try블록
// - (2) : catch블록 시작 직전, (1)이 모두 진행된 이후 or (1)에서 예외 발생 이후 catch로 가지 전
} catch (Exception e) {
// - (3) : catch블록
} finally {
// - (4) : finally블록
}
(1) 예외가 없을 경우 정상적으로 try블록 동작 or 예외가 있을 경우 예외가 발생한 코드 이후는 무시
(2) (1)에서의 두가지 경우가 발생하면 try-with-resource
는 Resource
의 close()
을 호출, 이때 close()
함수에서도 예외를 발생시킬 수 있으므로 (3)번 이전에 실행되어 예외를 처리?
(3) try블록에서 발생한 예외 혹은 close()
을 호출하면 발생한 예외처리, 하지만 catch는 하나의 예외만 처리할 수 있어 try블록의 예외 이후 close()
의 예외도 발생하면 try블록의 예외가 먼저 예외처리되고 close()
의 예외는 무시되는 것을 볼 수 있다.
(4) 모든 동작이 마무리되고 finally블록 동작
try-with-resource를 사용할 시 catch블록은 close()
의 예외를 처리하는 용도로 사용하는 것 같다. 그렇기 때문에 try블록 안에는 새로운 예외가 발생하지 않도록 해야할 것 같다.
throw
throw new Exception(param);
throws
try-catch
로 처리하든가 throws
를 통해 Call Stack의 상위 메소드에게 예외처리를 위임한다. 실제로 예외를 처리하는 것은 try-catch
이다.try/finally
throws
를 통해 상위 스택으로 위임하고 예외가 발생하거나 안하거나 finally블록을 통해 자원을 관리할 수 있도록 할 때 사용한다.Error
OutofMemoryError
이나 스택오버플로우 StackOverflowError
와 같이 복구할 수 없는 것을 말한다. 이러한 에러는 개발자가 예측하기도 쉽지 않고 처리할 수 있는 방법도 없다.Exception
ArrayIndexOutOfBoundsException
, 값이 null인 참조변수를 참조하는 경우 NullPointerException
, 존재하지 않는 파일의 이름을 입력하는 경우 FileNotFoundException
등이 있다. 다음과 같은 예외는 충분히 예측하고 처리할 수 있다. 예외는 CheckedException
과 UncheckedException
으로 나뉜다.CheckedException
CheckedException
이 발생하는 부분에서 try/catch
로 처리를 안해주면 컴파일 에러 발생, 또는 throws 로 던져야 한다.UncheckedException
UncheckedException
이 발생하는 부분에서 try/catch
로 처리를 강제하지 않아도 된다.RuntimeException
UncheckedException
을 상속한 클래스RuntimeException
을 상속받은 예외들은 명시적인 예외처리를 강제하지 않는다.Not RuntimeException
CheckedException
을 상속한 클래스RuntimeException
이 아닌 예외들은 명시적으로 예외처리를 해야한다.public class CustomException extends (Exception or RuntimeException) {
// 1. 매개 변수가 없는 기본 생성자
CustomException() {}
// 2. 예외 발생 원인(예외 메시지)을 전달하기 위해 String 타입의 매개변수를 갖는 생성자
CustomException(String message) {
super(message); // RuntimeException 클래스의 생성자를 호출합니다.
}
}
출처:
https://facingissuesonit.com/java-exception-handling/
https://codechacha.com/ko/java-try-with-resources/
https://ryan-han.com/post/java/try_with_resources/
https://velog.io/@youngerjesus/%EC%9E%90%EB%B0%94-%EC%98%88%EC%99%B8-%EC%B2%98%EB%A6%AC#the-finally-block
https://devlog-wjdrbs96.tistory.com/351
https://www.notion.so/3565a9689f714638af34125cbb8abbe8
https://veneas.tistory.com/entry/Java-%EC%BB%A4%EC%8A%A4%ED%85%80-%EC%98%88%EC%99%B8-%EB%A7%8C%EB%93%A4%EA%B8%B0Custom-Exception