동시성 프로그래밍 및 자바 (1) - 프로세스와 쓰레드의 차이

이동욱

2021/03/01

Categories: 프로그래밍 - 자바 Tags: 자바

동시성이란? (Concurrency)


동시성 프로그래밍이란?

Screen Shot 2021-03-01 at 2 13 30 PM

동시성에 대해서 자바 문서에서는 이렇게 설명하고 있다. 유저는 컴퓨터를 사용하면서 한 번에 한 가지 이상의 작업을 수행할 수 있다는 사실을 당연하게 여긴다. 그들은 워드 프로세서 작업을 하면서 파일을 다운로드 받거나, 프린트 인쇄 대기열을 관리하거나, 오디오 스트리밍을 할 수 있는다고 생각한다. 심지어 단일 응용 어플리케이션의 경우에도 한 번에 둘 이상의 작업을 해야할 때가 많다. 예를 들어서 스트리밍 오디오 애플리케이션은 네트워크에서 디지털 오디오를 동시에 읽고 압축을 풀고, 재생을 관리하고 디스플레이를 업데이트 해야합니다. 워드 프로세서 조차도 텍스트 서식을 변경하거나 디스플레이를 업데이트 하는 작업이 아무리 바쁘더라도 키보드 및 마우스 이벤트에 항상 응답을 할 준비가 되어있어야 합니다. 이러한 작업을 수행할 수 있는 소프트웨어를 동시성 소프트웨어라고 합니다. 자바 플랫폼은 동시성 프로그래밍을 지원하도록 처음부터 설계되었습니다. 자바 버전 5.0부터 자바는 높은 수준의 동시성 API를 포함하고 있습니다.1

프로세스와 쓰레드

Screen Shot 2021-03-01 at 2 29 04 PM

동시성 프로그래밍에서는 두가지의 기본 실행 단위가 있다. 자바에서는 동시성 프로그래밍은 주로 쓰레드와 관련이 있지만, 프로세스 역시 중요하다. 컴퓨터 시스템에서 일반적으로 많은 프로세스와 스레드가 있다. 이는 단일 코어 시스템에서도 마찬가지이다.

Screen Shot 2021-03-01 at 2 44 12 PM

프로세스

쓰레드

자바에서 쓰레드를 사용하는 방법


자바에서 쓰레드를 사용할 수 있는 방법에는 크게 3가지가 있다.

1. Thread를 상속 받는 방법


public class Main {
    public static void main(String[] args) {
        MyThread myThread = new MyThread();
        myThread.start();

        System.out.println("Hello");
    }

    static class MyThread extends Thread {
        @Override
        public void run() {
            System.out.println("Thread: " + Thread.currentThread().getName());
        }
    }
}

2. Runnable을 구현하는 방법


public class Main {
    public static void main(String[] args) {
        Thread thread = new Thread(new Runnable() {
            @Override
            public void run() {
                System.out.println("Thread: " + Thread.currentThread().getName());
            }
        });
        thread.start();
        System.out.println("Hello: " + Thread.currentThread().getName());
    }
}

3. 람다를 사용하는 방법


public class Main {
    public static void main(String[] args) {
        Thread thread = new Thread(() -> {
            System.out.println("Thread: " + Thread.currentThread().getName());
        });
        thread.start();
        System.out.println("Hello: " + Thread.currentThread().getName());
    }
}

쓰레드의 주요 기능


sleep

Screen Shot 2021-03-01 at 3 42 59 PM

public class Main {
    public static void main(String[] args) {
        Thread thread = new Thread(() -> {
            System.out.println("Thread: " + Thread.currentThread().getName());
            try {
                Thread.sleep(1000L);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        });
        thread.start();
        System.out.println("Hello: " + Thread.currentThread().getName());
    }
}

interrupt

Screen Shot 2021-03-01 at 3 42 22 PM

public class Main {
    public static void main(String[] args) throws InterruptedException {
        Thread thread = new Thread(() -> {
            while (true) {
                System.out.println("Thread: " + Thread.currentThread().getName());
                try {
                    Thread.sleep(1000L);
                } catch (InterruptedException e) {
                    System.out.println("interrupt!");
                    return;
                }
            }
        });
        thread.start();
        System.out.println("Hello: " + Thread.currentThread().getName());
        Thread.sleep(3000L);
        thread.interrupt();
    }
}

join

Screen Shot 2021-03-01 at 3 41 37 PM

public class Main {
    public static void main(String[] args) throws InterruptedException {
        Thread thread = new Thread(() -> {
            System.out.println("Thread: " + Thread.currentThread().getName());
            try {
                Thread.sleep(3000L);
            } catch (InterruptedException e) {
                throw new IllegalStateException(e);
            }
        });
        thread.start();

        System.out.println("Hello: " + Thread.currentThread().getName());
        thread.join();
        System.out.println(thread + " is finished");
    }
}

참고 문헌

>> Home