this page의 저자는 아래의 두 번째 코드 예는 동기화 문제가 있지만 코드는 100 번에서 약 99 번 작동한다고 언급합니다.이 페이지의 두 프로그램에서 작동상의 차이점을 볼 수 없습니다.다음과 같은 동기화 문제는 어떤 동기화 문제로 발생합니까?
이전 두 결합 다소 일반적인 솔루션은 다음에, 로컬 변수로 필드 값을 복사하여 로컬 변수를 변경하는 것이다. 메서드 내에서 필드는 변경되지 않습니다. 예를 들어,
public class Counter {
int count = 0;
public void count() {
int count = this.count;
int limit = count + 100;
while (count++ != limit) System.out.println(count);
}
}
참고 로컬 변수 카운트 필드 카운트 그림자 방법 및 키워드 그림자 외부 필드 수를 참조하는 데 사용되는 방법.
이 트릭은 변경된 변수를 메소드가 완료 될 때 필드에 다시 저장할 필요가없는 경우에 주로 유용합니다. 다음은 상태를 저장하지만 여전히 덜 분명한 동기화 문제의 영향을받습니다. 이 여기에 버그가 소스 코드에 자리하지 않는 경우 아래 핀 매우 열심히하는 (100)에서 99 시간을 작동하기 때문에
사실public class Counter {
private int count = 0;
public void count() {
int count = this.count;
int limit = count + 100;
while (count++ != limit) System.out.println(count);
this.count = count;
}
}
, 이것은 아마도 원래의 예보다 더 나쁘다 .
답변 해 주셔서 감사합니다. 이것이 저자가 의미하는 문제라면 대부분의 시간 이후로 대부분의 시간에 발생해야하며 두 번째 스레드는 첫 번째 스레드가 완료되기 전에 시작해야합니다. 그러나 저자는 프로그램이 100 회에서 99 회 작동한다고 말합니다. 따라서 프로그램 끝에 this.count의 의도 된 값이 200인지 확실하지 않습니다. –
"두 번째 스레드가 첫 번째 스레드가 시작되기 전에 시작됩니다"는 테스트되지 않은 어설 션입니다. 사실, 다른 실행 스레드를 생성하는 것이 100 반복 루프보다 빠르다면 놀랄 것입니다. 나는 테스트를 위해 그것을 실행하는 것이 좋습니다.물론 저자의 99 % 성공률에 대한 주장은 과장이 될 수도 있습니다 .-) – paxdiablo
@BM : 나는이 코드에서 다른 문제를 발견 할 수 없었습니다. 특히 다음 페이지에서 저자가 제안한 전체 메소드에서 od'synchronized' 키워드를 사용하여 해당 문제에 대한 가능한 해결책 중 하나를 선택하십시오. – Crozin