TIL

  1. wait(), notify()
  2. semaphore

 


 

wait(), notify()

  • 동기화 효율을 높이기 위해 wait(), notify()를 사용한다.
  • Object 클래스에 정의되어 있으며, 동기화 블록 내에서만 사용할 수 있다.
    • wait() : 객체의 lock을 풀고 스레드를 해당 객체의 waiting pool에 넣는다.
    • notify() : watiting pool에서 대기 중인 스레드 중 하나를 깨운다.(랜덤으로 깨운다)
    • notifyAll() : waiting pool에서 대기 중인 모든 스레드를 깨운다.(notify()보다 많이 사용함)

 

class Account {
    private int balance = 1000; // 잔금

    public syncronized void withdraw(int money) {
        while (balance < money) {
            try { 
                wait(); // 대기 - lock을 풀고 기다린다. notify() 받으면 lock을 재획득
            } catch (InterruptedException e) {}
        }
        balance -= money;
    }

    public syncronized void deposit(int money) {
        balance += money;
        notify(); // 통지 - 대기 중인 스레드 중 하나에게 알림
    }
}

 

 

 

 

Semaphore

class 계좌 {
   public synchronized int 잔금조회() {}
   public syncronized void 출금하기() {}
} 

스레드A가 lock을 갖고 출금하기()를 실행하고 있으면 스레드B가 잔금조회()를 실행할 수 없다. 스레드A가 해당 객체의 lock을 점유했기 때문이다. 이 부분은 Java monitor가 처리해준다. 만약 lock 하나에 여러 스레드가 접근할 필요가 있다면 Thread 수를 제어할 수 있는 Semaphore가 있다! 예를 들어,

 

 

Semaphore semaphore = new Semaphore(3);

semaphore는 최대 3개의 스레드가 동시에 공유 객체에 접근할 수 있다는 뜻이다.
하지만 이 3개의 스레드들끼리의 동기화는 보장하지 않는다. 음... 근데 semaphore를 사용할 때는 언제일까? 아직 감이 안 잡힌다. 일단 이런 키워드가 있다는 정도로 기억해두자!

 

 

 

 

📚 참고
자바의 정석