728x90
반응형
SMALL
예외
- 컴파일 에러는 문법상의 오류로 컴파일러가 고쳐주는 경우가 많다
- 예외 (Exception) 은 문법상의 오류가 아닌 실행중에 발생되는 오류 상황을 말한다.
- 기본적으로 예외가 발생되면, 예외 관련 메세지를 출력하고 프로그램이 종료된다.
- 예외 객체층
java.lang.Object
|__ java.lang.Throwable
|
|__ java.lang.Exception : 복구 가능
| |
| |__ java.lang.RuntimeException
| | |__ ArithmeticException, NullPointerException, ArrayIndexOUtOfBoundsException ...
| |
| |__ IOException, ParseException ...
|
|__ java.lang.Error : 복구 불가
... OutOfMemoryError, StackOverFlowError ...
- Object 클래스가 Throwable 클래스의 상속을 받고 그 밑으로 RuntimeException, IOException 등이 상속받는다.
- getMessage(), printStackTrace() 등의 메소드는 Throwable 클래스에 정의되어있기 때문에 오버라이드 하여 사용 할 수 있다.
예외 처리 TRY~CATCH
- 예외 처리를 할 때 try ~ catch ~ 문을 사용하는데 그 이유는 if문은 예외 처리 이외의 용도로 사용되기 때문에 예외처리를 구분 하는데 어려움이 있다.
- try문에는 일반적인 흐름을 작성한다.
- catch문에서는 예외처리(handling 이라고 표현) 블럭으로 만들어서 코드 분석이 훨씬 용이하다.
- 예제
// if 문을 사용한 처리
if (num2 != 0) {
result = num1 / num2;
} else {
System.out.println("0으로 나눌 수 없습니다... ");
} // end if
System.out.println("결과: " + result);
// 위의 코드를 try~catch 로 만들어 처리
try{
result = num1 / num2;
System.out.println("결과: " + result);
} catch(ArithmeticException ex) {
// catch{ .. } 예외 처리 블럭. 예외 발생시 수행되는 코드들.
// 위 try 블럭 수행중에 ArithmeticException 이 발생(throw)되면 이를 처리(handling)하는 catch 블럭
System.out.println("0으로 나누는 Exception");
System.out.println(ex.getMessage());
ex.printStackTrace();
}
- 특히 시스템 자원, HW(하드웨어. DB) 등의 네트워크를 사용하는 프로그래밍에서는 예외가 언제든지 발생할 수 있기때문에 try~catch 문이 필수적이다.
FINALLY
- 예외 발생의 여부와 상관없이 항상 실행 되어야할 코드블럭
- finally 블럭 안에 있는 코드들은 항상, 반드시 실행
- 예외가 발생했을 때
- try (예외 발생) -> catch -> finally
- 예외 발생하지 않을 때
- try -> finally
- try 나 catch 블럭 안에 return 이 있더라고 finally 블럭의 코드를 실행 한 이후에 return 을 실행하게 됨 **
- 예제
System.out.println("#1 try{} 직전");
try{
System.out.println("#2 try{} 시작");
// Integer.parseInt("abc");
int[] numbers = new int[10];
numbers[10] = 123;
System.out.println("#3 try{} 종료");
} catch (ArrayIndexOutOfBoundsException ex){
System.out.println("#4 catch{} 시작");
System.out.println("예외메세지: " + ex.getMessage());
//System.out.println("#5 catch{} 종료");
//return;
} finally {
System.out.println("#6 finally{}");
}
System.out.println("#7 try 종료");
thorws
- 메소드를 설계 할 때, 예외 처리를 직접 하지 않는 경우
- 메소드 이름 뒤에 throws Exception을 추가하면 예외가 발생 했을 때, 메소드를 호출 한 곳으로 exception이 던져짐
- Exception 혹은 Exception을 상속받은 예외를 throws 하는 메소드는 반드시 호출하는 쪽에서 예외처리가 되어야한다.(하지 않을 경우 uncheck exception)
- 하지만 RuntimeException 혹은 이를 상속받은 예외를 throws하는 메소드는 굳이 예외 처리를 해주지 않아도 된다.
- 예제
public class TestClass {
// throws x
public int divide(int x, int y) {
int result = 0;
try{
result = x / y;
} catch (ArithmeticException ex){
System.out.println(ex.getMessage());
}
return result;
} // end divide()
// 메소드 설계를 할 때 예외 처리를 직접 하지 않는 경우:
// 메소드 이름 뒤에 throws Exception을 추가하면,
// 예외가 발생한 경우에는 메소드를 호출한 곳으로 exception이 던져짐.
// Exception 및 이를 '직접 상속받은' Exception 을 throws 하는 메소드의 경우,
// 이 메소드를 호출하는 쪽에서 반.드.시 예외 처리 (handling) 해야 한다. 안하면 에러!
public int divide2(int x, int y) throws Exception {
return x / y;
} // end divide2()
// 반면 'RuntimeException' 및 이를 상속받은 예외를 throws 하는 메소드는
// 굳이 호출하는 쪽에서 매번 예외 처리 할 필요는 없다
public int divide3(int x, int y) throws RuntimeException{
return x / y;
} // end divide3()
} // end class TestClass
public class Exception06Main {
public static void main(String[] args) throws Exception {
System.out.println("throws");
System.out.println();
TestClass test = new TestClass();
int result = test.divide(123, 0);
System.out.println("result = " + result);
System.out.println();
try {
//test.divide2(123, 0);
} catch (Exception e) {
throw new RuntimeException(e);
}
// test.divide2(111, 0); // 만약에 try-catch 안할거면 main 메소드가 throws Exception 을 해줘야 한다.
// main() 메소드는 가상머신이 호출하는 메소드이다. 예외상황 처리는 가상머신에게 넘어간다
// 가상머신의 예외처리 순서
// 1 : getMessage 호출
// 2 : 예외상황이 발생해서 전달되는 과정 출력
// 3 : 프로그램 종료
//test.divide3(111,0);
Thread.sleep(1000);
System.out.println("프로그램 종료...");
} // end main()
} // end class Exception06Main
CustomException
- Exception을 직접 만들어서 사용할 수 있다
- Exception & RuntimeException 클래스를 상속 받아서 만듬
- 예제
// 아래와 같이 Exception 을 상속받아 예외 클래스를 정의해 주었음
public class ScoreException extends Exception{
// 생성자
public ScoreException(){
super("점수 입력오류");
}
public ScoreException(String msg){
super(msg);
}
} // end class ScoreException
public class Exception07Main {
static Scanner sc = new Scanner(System.in);
//inputScore() 메서드에 ScoreException throws
public static int inputScore() throws ScoreException{
int score = sc.nextInt();
if(score < 0 || score > 100){ // 예외발생
// ScoreException ex = new ScoreException();
var ex = new ScoreException(score + "는 유효한 숫자가 아닙니다");
throw ex; //예외 객체를 throw
}
return score;
} // end inputScore()
public static void main(String[] args) {
System.out.println();
try{
System.out.println("국어 점수 입력:");
int kor = inputScore();
System.out.println("kor = " + kor);
System.out.println("영어 점수 입력:");
int eng = inputScore(); // 메소드레서 throws를 해주었기 때문에 호출한 곳으로 넘어옴
System.out.println("eng = " + eng);
}catch(ScoreException e){
System.out.println(e.getMessage());
}finally {
sc.close();
}
} // end main()
} // end class Exception07Main
728x90
반응형
LIST
'프로그래밍 > 자바' 카테고리의 다른 글
[자바/기본] Wrapper 클래스란? (Boxing, UnBoxing) (1) | 2024.02.06 |
---|---|
[자바/기본] String 클래스/ StringBuilder / StringBuffer / StringTokenizer (1) | 2024.01.22 |
[자바/기본] 인터페이스 Interface + 추상 클래스 Abstract + 다형성 Polymorphism (0) | 2023.10.12 |
[자바/기본] 상속 Inheritance (0) | 2023.10.12 |
[자바/기본] Modifier 제어자 (0) | 2023.10.10 |