2013-03-08 5 views
0

과제에 대해 Java에서 카운팅 세마포를 만들어야합니다. 나는 지금까지 내가 혼란 내가 대기 (에 차단 함)와 반대로 어떻게() 신호에 하나의 스레드 차단을 해제 할 방법을 정확하게되어있어 지금의이 베어 뼈 클래스차단 및 차단 해제 방법에 대한 세마포어

public class Semaphore { 
    int value; 

    public Semaphore(int value) { 
     this.value = value; 
    } 

    public static void wait(Semaphore s) { 
     s.value--; 
     if (s.value < 0) { 
      // block 
     } 
    } 

    public static void signal(Semaphore s) { 
     s.value++; 
     if (s.value <= 0) { 
      // unblock one process that is blocked on semaphore 
     } 

    } 
} 

을 만들었습니다? 차단 된 대기열이 있지만 그 대기열에 대한 참조는 어디에 보관합니까?

+0

어떤 잠금 프리미티브를 허용 했습니까? [Object # wait()] (http://docs.oracle.com/javase/7/docs/api/java/lang/Object.html#wait())? –

+1

'wait()'와'signal()'을 인스턴스 메소드로 구현하지 않는 이유는 무엇입니까? 세마포어는 정의 상 다중 스레드에 의해 호출됩니다. 코드가 스레드로부터 안전하도록 동기화가 필요합니다. (Object가 이미'wait()'메소드를 가지고 있기 때문에'wait()'는'await()'(또는 다른 것)으로 명명되어야 함을주의하라. –

답변

1

대기 메서드 (대기 이외의 다른 메서드라고도 함)에서 값이 0이면 0인지 확인해야합니다 , 당신은 단지 계속 기다리고 있습니다. 이것은 다음에서 이루어집니다 :

public synchronized void P() throws InterruptedException 
{ 
    while (value == 0) 
    { 
     wait(); 
    } 
    value--; 
} 

귀하의 방법은 세마포어 개체를 사용하지 않습니다. 세마포어 클래스의 값 필드를 사용하기 만하면됩니다.

이 메서드는 값이 0 인 동안 값이 변경 될 때까지 대기하는지 확인합니다. 따라서 메서드를 호출 한 곳의 스레드가 기다려야합니다. 그렇지 않은 경우 값이 0이 아닌 경우 스레드는 해당 임계 영역에 진입 할 수 있으며 값이 0이 될 때까지 값이 감소합니다. 즉 스레드가 차단됩니다.

신호 방법은 값을 증가시켜 임계 값을 입력 할 수 있는지 값을 변경하려고 기다리고있는 스레드에게 알려야합니다. 신호 방법은 다음에서 구현됩니다 : 나는 방법에 사용

public synchronized void V() 
{ 
    value++; 
    notify(); 
} 

의 이름 지정은 다 익스트라가 세마포어에 사용되는 이름에서 비롯됩니다 (다만 경우에 당신이 그들에 의해 혼동하고 있습니다).

차단 메서드를 Object에서 wait 메서드와 혼동하기 때문에 wait 메서드를 호출하면 안됩니다.

+1

+1. Dijkstra는 네덜란드에서 왔기 때문에 BTW P()와 V()와 같은 언어를 사용했습니다. –

+0

고마워요,이게 너무 많은 도움이되었습니다! – Ziamor

0

wait()/notify() 메소드를 사용하십시오. 객체를 호출하기 전에 객체 잠금을 가져와야합니다. 즉, 메서드를 비 정적으로 만들어 동기화 된 것으로 표시해야합니다.