java - 경쟁 조건 인터뷰 질문:정수의 최소 및 최대 범위




multithreading race-condition (2)

나는 최근에 인터뷰에서이 질문을 받았다.

다음 코드가 주어지면 정적 정수 num 의 가능한 최소값과 최대 값은 얼마입니까?

import java.util.ArrayList;
import java.util.List;

public class ThreadTest {
    private static int num = 0;

    public static void foo() {
        for (int i = 0; i < 5; i++) {
            num++;
        }
    }

    public static void main(String[] args) throws Exception{
        List<Thread> threads = new ArrayList<Thread>();
        for (int i = 0; i < 5; i++) {
            Thread thread = new Thread(new Task());
            threads.add(thread);
            thread.start();
        }
        for (int i = 0; i < 5; i++) {
            threads.get(i).join();
        }
        // What will be the range of num ???
        System.out.println(ThreadTest.num);
    }
}

class Task implements Runnable {
    @Override
    public void run() {
        ThreadTest.foo();
    }

}

최대 값은 25 (경쟁 조건이없는 경우)이고 최소값은 5 ​​(모든 반복에서 모든 스레드 간 경합 조건의 경우)가 될 것이라고 말했습니다.
그러나 면접관은 최소값이 5보다 낮을 수도 있다고 말했다.
어떻게 가능합니까?


가능한 최소값은 2라고 주장합니다.

이것의 핵심은 num++ 의 비원 자성입니다. 즉, 읽기와 쓰기이며, 그 사이에 다른 연산이있을 수 있습니다.

스레드 T1..T5를 호출하십시오.

  • T1은 0을 읽고 T2는 0을 읽고;
  • T1은 1을 쓴 다음 3 번 읽고 쓴다.
  • 그런 다음 T2는 1을 씁니다.
  • 그런 다음 T1은 1을 읽습니다.
  • 그런 다음 T2-5는 모든 작업을 수행합니다.
  • 그런 다음 T1은 2를 씁니다.

(참고 : 결과 2는 스레드 수 또는 반복 횟수에 의존하지 않으며, 각각 2 개 이상이 있어야합니다.)

그러나 이것에 대한 정직한 대답은 실제로 중요하지 않습니다. JLS 17.4.5에 정의 된대로 데이터 경쟁이 있습니다.

프로그램에 발생 전 관계에 의해 순서가 정해지지 않은 두 개의 상충되는 액세스 (§17.4.1)가 포함 된 경우, 데이터 경쟁 을 포함한다고합니다.

(스레드의 조치 사이에 발생 전 관계가 없음)

따라서 무엇을하든 유용하게 사용할 수 없습니다. 단순히 잘못된 코드입니다.

(또한, 멀티 스레드 코드 디버깅이나 심도있는 기술 독서로 인해 어려운 대답이 아니라는 것에 대한 답을 알고 있습니다. 다른 곳보다 먼저이 답변을 읽었 기 때문에 이것을 알고 있습니다. 팔러 트릭입니다. 최소값 은 좋은 면접 질문이 아닙니다).


글쎄, 내 대답은 Max 25, Min 0입니다. 모든 작업이 증가하고 0으로 초기화했기 때문에 정적 비 휘발성 int가 거기에 던져져 인종에 대한 이러한 생각을하게합니다. 조건이 있지만 어떤 상황에서도 숫자를 줄일 수있는 것이 있습니까?

편집 : 가치있는 것에 대해, 이것은 당신이 현실 세계에서 극복 할 수 있다고 기대할 수있는 전형적인 산만 일 것입니다. 그러한 "속임수"를 정당화하십시오. 많은 붉은 청어가 있습니다!





race-condition