>  기사  >  Java  >  Java 스레드에 대한 발생 전 규칙은 무엇입니까?

Java 스레드에 대한 발생 전 규칙은 무엇입니까?

WBOY
WBOY앞으로
2023-04-14 19:07:101337검색

Text

happens-before는 공유 변수에 대한 쓰기 작업이 다른 스레드의 읽기 작업에 표시되도록 규정합니다. 이는 가시성과 순서에 대한 일련의 규칙을 요약한 것입니다. JMM은 다음과 같은 발생 전 규칙을 보장할 수 없습니다. 스레드가 공유 변수에 쓰는 것은 다른 스레드가 공유 변수를 읽는 것을 볼 수 있습니다.

사례 1

스레드가 m을 잠금 해제하기 전에 변수에 쓰는 것은 나중에 m을 잠그는 다른 스레드가 변수를 읽는 것을 볼 수 있습니다.

    static int x;
    static Object m = new Object();

    new Thread(()->{
         synchronized(m) {
         x = 10;
         }
    },"t1").start();

    new Thread(()->{
         synchronized(m) {
         System.out.println(x);
         }
    },"t2").start();
/*
运行结果:
10
*/

사례 2

스레드가 휘발성 변수를 쓰는 것은 다른 스레드가 이후에 변수를 읽을 때 볼 수 있습니다.

    volatile static int x;
    new Thread(()->{
     x = 10;
    },"t1").start();

    new Thread(()->{
     System.out.println(x);
    },"t2").start();
/*
运行结果:
10
*/

케이스 3

스레드가 시작되기 전에 변수를 쓰는 것은 휘발성 변수에 보입니다. 스레드가 시작된 후 변수 읽기

static int x;
x = 10;
new Thread(()->{
 System.out.println(x);
},"t2").start();
/*
运行结果:
10
*/

사례 4

스레드가 끝나기 전에 변수에 쓴 내용은 종료된 것을 알고 난 후 다른 스레드에서 볼 수 있습니다(예: t1.isAlive() 또는 t1.join을 호출하는 다른 스레드) () 끝날 때까지 기다리기)

static int x;
Thread t1 = new Thread(()->{
 x = 10;
},"t1");
t1.start();
t1.join();
System.out.println(x);
/*
运行结果:
10
*/

사례 5

t2(인터럽트)를 중단하기 전에 스레드 t1이 변수를 쓰는 것은 t2가 중단되었음을 알고 난 후(t2.interrupted 또는 t2.isInterrupted를 통해) 다른 스레드에서 볼 수 있습니다.

static int x;
public static void main(String[] args) {
    
     Thread t2 = new Thread(()->{
         while(true) {
             if(Thread.currentThread().isInterrupted()) {
             System.out.println(x);
             break;
             }
         }
     },"t2");
     t2.start();
    
     new Thread(()->{
         sleep(1);
         x = 10;
         t2.interrupt();
     },"t1").start();
     while(!t2.isInterrupted()) {
         Thread.yield();
     }
     System.out.println(x);
}
/*
运行结果:
10
*/

Case 6

변수 기본값(0, false, null) 쓰기는 다른 스레드가 변수

    static int a;
    public static void main(String[] args) {
        new Thread(()->{
            System.out.println(a);
        }).start();

    }
/*
运行结果:
0
*/

Case 7

을 읽을 때 볼 수 있습니다. y hb-> z x hb -> z가 있으며 휘발성의 반명령 재배열과 결합되어 다음과 같은 예가 있습니다

volatile static int x;
static int y;
new Thread(()->{ 
 y = 10;
 x = 20;
},"t1").start();
new Thread(()->{
 // x=20 对 t2 可见, 同时 y=10 也对 t2 可见
 System.out.println(x); 
},"t2").start();
/*
运行结果:
20
*/

위 내용은 Java 스레드에 대한 발생 전 규칙은 무엇입니까?의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

성명:
이 기사는 yisu.com에서 복제됩니다. 침해가 있는 경우 admin@php.cn으로 문의하시기 바랍니다. 삭제