당신은 특정 개체에 대한 몇 가지 지정된 정적 락 객체, 또는 (정적 방법은 동기화 할 선언 할 때 발생) 클래스 객체 중 하나를 동기화 :
class X {
private static final Object lock = new Object();
public void oneAtATime() {
synchronized (lock) {
// Do stuff
}
}
}
class Y {
public void oneAtATime() {
synchronized (Y.class) {
// Do stuff
}
}
}
각 변형이 자신의 장단점이 있습니다를 ; 클래스를 잠그면 클래스 외부의 다른 코드가 자물쇠를 사용하여이를 금지하는 자체적 인 이유 (사용자가 제공하는 것보다 더 높은 수준의 동기화를 조정할 수 있음)에 대해 동일한 잠금을 사용할 수 있습니다. static final Object lock
접근 방식을 사용하면 잠금 private 필드 (잠금을 추론하는 것이 더 쉬워지고 다른 사람이 잘못된 코드를 작성했기 때문에 교착 상태에서 코드를 피할 수 있습니다).
당신은 물론 또한 잠금 (및 ReentrantLock
것은 현재 높은 경쟁에서 암시 잠금보다 조금 더 나은 수행)을 통해 더 많은 제어를 제공 명시 적 Lock
들처럼, java.util.concurrent
일부 동기화 메커니즘을 사용할 수 있습니다. 그것을 만들기에서 어떤 옆으로 지금까지 본질적으로 다른 모든 인스턴스에 연결됩니다 만든 클래스의 모든 인스턴스 (의미 - 정적/글로벌 잠금이 갈 수있는 좋은 방법이 아니라는 것을 참고 : 편집
코드를 테스트하거나 읽는 것이 더 어려우므로 확장성에 심각한 영향을 미칠 수 있음). 나는 어떤 종류의 세계적인 상태를 동기화하기 위해 이것을한다고 가정합니까? 이 경우 전역/정적 상태를 대신 클래스로 래핑하고 전역으로 동기화하지 않고 인스턴스별로 동기화를 구현하는 방법을 고려해 보겠습니다.대신에 이런 일의 :
class Z {
private static int state;
public void oneAtATime(){
synchronized (Z.class) {
state++;
}
}
}
이처럼 수행
class State {
private int value;
public synchronized void mutate(){ value++; }
}
class Z {
private final State state;
public Z(State state){
this.state = state;
}
public void oneAtATime(){
state.mutate();
}
}
// Usage:
State s1 = new State(), s2 = new State();
Z foo = new Z(s1);
Z bar = new Z(s1);
Z frob = new Z(s2);
Z quux = new Z(s2);
이제 foo
및 bar
는 여전히 서로 연결되어 있지만 frob
및 quux
에서 독립적으로 작업 할 수 있습니다. 정적 클래스의 필드 또는 클래스 자체에
왜 이렇게해야하는지 설명 할 수 있습니까? 나는 당신이 잘못된 문제를 공격하고 있다는 느낌을 가지고 있습니다. 실제 문제가 다른 곳에서와 같이 * 완전히 다른 클래스 인스턴스에서 메소드 호출을 동기화해야합니다. –