Mutex와 Semaphore
2024. 10. 20. 16:33ㆍ개발/Java
Mutex
- 동시 프로그래밍에서 공유 불가능한 자원의 동시 사용을 피하기 위해 사용하는 알고리즘
- 임계구역(Critical Section)을 가진 스레드들의 실행시간(Running Time)이 서로 겹치지 않고 각각 단독으로 실행(상호배제_Mutual Exclution)되도록 하는 기술
- 한 프로세스에 의해 소유될 수 있는 Key를 기반으로 한 상호배제 기법
- Key에 해당하는 어떤 객체(Object)가 있으며, 이 객체를 소유한 스레드/프로세스만이 공유자원에 접근할 수 있다.
여기서 설명하는 Key를 소유한다는게 Java로 따지면 Lock을 얻는 것이라고 할 수 있을 듯…
synchronized키워드를 사용하는 것이 Mutex 알고리즘을 사용하는 것이다.
ReentrantLock은 자바에서 락을 명시적으로 획득하고 해제하는 Mutex를 이용하는 고급 동기화 도구이다.
Semaphore
Semaphore는 특정 자원에 대해 동시에 여러 쓰레드가 접근할 수 있도록 하는 메커니즘. Semaphore는 내부적으로 **카운터(공통으로 관리하는 하나의 값)**를 사용하여 몇 개의 쓰레드가 동시에 자원에 접근할 수 있을지를 제어한다.
- Semaphore(n): 최대 n개의 쓰레드가 동시에 자원에 접근할 수 있습니다. 쓰레드가 자원에 접근할 때마다 카운터를 감소시키고, 자원을 해제할 때마다 카운터를 증가시킨다.
- 쓰레드가 자원에 접근하려고 할 때 카운터가 0이면, 쓰레드는 자원을 사용할 수 있을 때까지 대기하게 된다.
Semaphore와 관련된 Java 도구
Semaphore 클래스:
- Java에서는 Semaphore 클래스를 통해 여러 쓰레드가 동시에 자원에 접근할 수 있도록 관리할 수 있다.
- 카운팅 세마포어의 일종으로, 기본적으로 카운터를 통해 쓰레드의 접근을 관리한다.
Semaphore에서 설정한 스레드 안에서는 동시성이 보장이 되는가?
public static void main(String[] args) throws InterruptedException {
Semaphore semaphore = new Semaphore(2);
MyRunnable myRunnable = new MyRunnable(semaphore);
for (int i = 1; i <= 2; i++) {
Thread t = new Thread(myRunnable, "Thread-" + i);
t.start();
}
Thread.sleep(5000);
System.out.println("myRunnable = " + myRunnable.count);
}
static class MyRunnable implements Runnable {
private final Semaphore semaphore;
int count = 0;
public MyRunnable(Semaphore semaphore) {
this.semaphore = semaphore;
}
@Override
public void run() {
System.out.println("실행 시작");
try {
semaphore.acquire();
for (int i = 1; i <= 100; i++) {
count += i;
Thread.sleep(10);
}
semaphore.release();
} catch (InterruptedException e) {
throw new RuntimeException(e);
}
}
}
위처럼 어떤 공유자원에 대해 Semaphore 안에서 동시성이 보장이 안되는 것을 확인하였다.
new Semaphore(2);처럼 해줬을 때 값이 제대로 나오는 것을 확인하였다.
Mutex와 Semaphore의 차이
'개발 > Java' 카테고리의 다른 글
equals()와 hashcode() (0) | 2024.11.30 |
---|---|
ThreadLocal과 ThreadLocalMap (0) | 2024.11.17 |
메모리 가시성 (0) | 2024.10.20 |
동기화 (0) | 2024.10.05 |
스레드 제어와 생명 주기 (0) | 2024.10.02 |