본문 바로가기
JAVA/JAVA

[JAVA] 08. 예외처리, 스레드

by ssunooo 2024. 7. 24.

 

 

예외처리

프로그램을 이용하다가 예외가 발생하게되면 프로그램이 즉시 종료(비정상 종료)되기 때문에
예외를 개발자가 미리 처리해야 한다.

그러므로 예외처리를 하는 이유는
프로그램이 비정상적으로 종료되는 것을 예방하기 위함이다.

 

예외처리를 하는 방법으로는

먼저, 프로그램을 실행하다가 오류가 나면

오류가 난 예

 

위 그림과 같이 몇번째 줄에서 오류가 났는지 확인 할 수 있다.

11번째줄에 ArrayIndexOutOfBoundsException 의 예외가 발생한 것을 확인 가능하다.

 

이 때, 오류를 해결하는 방법에는 두가지가 있다.

코드를 오류가 나지않게 고쳐주는 것과

예외발생한 코드를 try-catch문을 통해 예외처리를 해주는 방법이다.

 


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
package exception;
 
import java.util.InputMismatchException;
import java.util.Scanner;
 
public class Test02 {
    public static void main(String[] args) {
        Scanner sc=new Scanner(System.in);
        
        int[] datas= {10,0,-1,2,3};
        int num1;
        int num2;
        
        while(true) {
            try {
                System.out.print("정수1 입력 >> ");
                num1=sc.nextInt();
            }
            catch(InputMismatchException e) {
                sc.nextLine();
                System.out.println("다시 입력해주세요!");
                continue;
            }
            break;
        }
        
        try {
            num1=datas[num1];
        }
        catch(ArrayIndexOutOfBoundsException e) {
            System.out.println("없는 인덱스 번호를 입력해서 [0]값으로 설정했습니다.");
            num1=datas[0];
        }
        
        while(true) {
            try {
                System.out.print("정수2 입력 >> ");
                num2=sc.nextInt();
            }
            catch(InputMismatchException e) {
                sc.nextLine();
                System.out.println("다시 입력해주세요!");
                continue;
            }
            break;
        }
        try {
            num2=datas[num2];
        }
        catch(ArrayIndexOutOfBoundsException e) {
            System.out.println("없는 인덱스 번호를 입력해서 [0]값으로 설정했습니다.");
            num2=datas[0];
        }
        
        try {
            int answer=num1/num2;
            System.out.println(num1+" / "+num2+" = "+answer);
        }
        catch(ArithmeticException e) {
            System.out.println("0으로는 나누기를 진행할 수 없습니다!");
            e.printStackTrace();
        }
        
    }
}
 
cs

 

위의 코드는 예외가 발생한 모든 코드들을 예외처리 해준 코드이다.

 

먼저 입력받는 부분에서 nextInt()로 정수로 받아야하는데 사용자가 문자열을 입력한 경우,

예외처리가 발생한 입력부분인 num1=sc.nextInt(); 부분을 try로 설정해

catch(InputMismatchException e) catch 안에 들어있는 예외가 발생할경우

while문을 반복하여 다시 입력할 수 있도록 사용했다.

 

그 다음으로 많이 예외가 발생하는 부분인 배열크기에 맞지않는 인덱스를 불러온 경우,

예외처리가 발생한 입력부분인 num1=datas[num1]; 부분을 try로 설정하고

(ArrayIndexOutOfBoundsException e) catch 안에 들어있는 예외가 발생할경우

0번 index로 바꿀 수 있게 사용했다.

 

마지막으로 0으로 나누기를 진행할 수 없는데 0으로 나누기를 진행한 경우,

예외처리가 발생한 부분인 int answer=num1/num2; 부분을 try로 설정하고

catch(ArithmeticException e) catch 안에 들어있는 예외가 발생할경우

"0으로 나누기를 진행할 수 없습니다"를 출력했다.

 


스레드

스레드는 실질적으로 일을 수행하는 주체로

스레드를 구현하는 데에는 두가지 방법이 있다.

 

첫번째로 스레드의 구조를 알고있거나,

두번째로 인터페이스를 활용한다.

 

이렇게 스레드를 여러개 진행할 경우

스레드는 병렬적으로, 개별적으로, 비동기적으로 일을 수행하기 때문에

누른 순서대로가 아닌 메모리가 적은 프로그램이 먼저 수행된다.

그러므로 화면에 출력되는 순서는 랜덤이다.

 

랜덤으로 실행되다보면 동시에 어떤일을 수행할 때 가 있는데

이럴때, 공유자원으로부터 접근을 제한하기 위해

블로킹 락을 이용해 동시에 일을 수행하지 않게 만들어 줄 수 있다.

 


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
package thread;
 
class Person implements Runnable { // 실질적으로 buy()를 수행하는 주체 == 스레드
    private TicketPage page; // buy()를 실행하려면 ticketpage 클래스가 필요해서 
    public Person(TicketPage page) {
        this.page=page;
    }
    @Override
    public void run() {
        this.page.buy();
    }
    
}
 
class TicketPage {
    private static int ticket=3// 공유자원
    public synchronized void buy() { // 동기화 <-> 비동기적으로 일을 수행하는 스레드
        if(TicketPage.ticket>0) {
            TicketPage.ticket--;
            System.out.println(Thread.currentThread().getName()+"님이 티켓을 구매하셨습니다."); // currentThread() = 현재 동작중인 스레드의 이름
        }
        else {
            System.out.println(Thread.currentThread().getName()+"님이 티켓 구매 실패....ㅠㅠ");
        }
    }
}
 
public class Test02 { // JAVA에서는 단독으로 쓸일이없다.
    public static void main(String[] args) {
        
        TicketPage page=new TicketPage();
        
        Thread t1=new Thread(new Person(page),"티모"); // 스레드 클래스는 생성자 오버로딩이 되어있다.
        Thread t2=new Thread(new Person(page),"아리");
        Thread t3=new Thread(new Person(page),"아무무");
        Thread t4=new Thread(new Person(page),"럭스");
        Thread t5=new Thread(new Person(page),"제드");
        
        t1.start();
        t2.start();
        t3.start();
        t4.start();
        t5.start();
        
    }
}
 
cs

 

 

2024.07.24