[Java] 쓰레드의 구현과 실행

nathan·2022년 1월 24일
0

JAVA

목록 보기
27/45

쓰레드의 구현과 실행

1) Thread 클래스 상속

class MyThread extends Thread {
   public void run () { // Thread 클래스의 run()을 오버라이딩
      // 작업 내용
   }
}

사용

MyThread t1 = new MyThread(); // 쓰레드의 생성
t1.start(); // 쓰레드의 실행

2) Runnable 인터페이스 구현

class MyThread2 implements Runnable {
   public void run() { // Runnable 인터페이스의 추상메서드 run()을 구현
      // 작업 내용
   }
}

사용

Runnable r = new MyThread2();
Thread t2 = new Thread(r); // Thread(Runnable r)
// Thread t2 = new Thread(new MyThread2());
t2.start(); // 쓰레드의 실행

예제 코드

public class Ex13_1 {
    public static void main(String[] args) {
        ThreadEx1_1 t1 = new ThreadEx1_1();

        Runnable r = new ThreadEx1_2();
        Thread t2 = new Thread(r); // 생성자 Thread(Runnable target)

        t1.start();
        t2.start();
    }
}

class ThreadEx1_1 extends Thread { // 1. Thread 클래스를 상속해서 쓰레드를 구현
    @Override
    public void run() { // 쓰레드가 수행할 작업을 작성
        for (int i = 0; i < 5; i++) {
            System.out.println(this.getName()); // 조상인 Thread의 getName()을 호출
        }
    }
}

class ThreadEx1_2 implements Runnable { // 2. Runnable 인터페이스를 구현해서 쓰레드를 구현
    @Override
    public void run() { // 쓰레드가 수행할 작업을 작성
        for (int i = 0; i < 5; i++) {
            // Thread.currentTread() - 현재 실행중인 Thread를 반환한다.
            System.out.println(Thread.currentThread().getName());
        }
    }
}

실행 결과

  • 지금은 순차적으로 t1, t2 쓰레드가 수행된 것 같지만, for문의 반복 횟수를 500씩으로 늘리면 다음과 같이 된다.
000011100000000000000000000000000000000000001111111111111111111111111111110000
000000000000000000011111111011111001110000100110111111111111111110111100000000
000000000011111111111100011111000000001111110001111111110000000000000000000001
111111100000001000001111111111000000000000000000000000000000000000000000000111
111111101111111111111111111100000001111111111111111110000000001111110000000000
000000000001111111111111000000111111111111111111111000000111100000000000111111
111111111111110001101111001110000011111111000000000000000000001100000000000111
111110000000000000000000000000000000001111111110000000011110000000000000011111
111111110001110000000001111111111111100000001111111111111111111111111111111111
111111111111000000000000001111111111111111100010011111111111111111111100111111
111111110000000000000000000000011111111100111111111111100000011000111110001100
000000011111000011000011000111110001111100000011000000000000000000000001111100
0000000000000000000000111111100001111111111111111111111111111111

쓰레드의 실행 - start()

  • 쓰레드를 생성한 후에 start()를 호출해야 쓰레드가 작업을 시작한다.
  • 위의 예제의 경우 순차적으로 실행된 것 같지만, t1이 먼저 start() 됐다고 해서 반드시 먼저 수행되는 것은 아니다.
    • 쓰레드를 start()하는 것은 "실행 가능한 상태" 를 만드는 것이지 바로 실행하는 것이 아니기 때문
    • 언제 실행할지는 OS의 스케쥴러가 결정한다. (OS 스케쥴러가 실행순서를 결정)

run()을 작성하는데 start()를 호출하는 이유?

  • start를 통해 새로운 Call stack(호출 스택)을 생성한다.
  • 새롭게 생성된 호출 스택에서 run()이 돌아간다고 생각하면 된다.
  • 각각의 쓰레드가 자기만의 호출 스택을 갖고 실행됨 (따라서 독립적 수행이 가능)
profile
나는 날마다 모든 면에서 점점 더 나아지고 있다.

0개의 댓글