标签:str 连续 案例 静态方法 source bsp 之间 使用权 block
原子性问题的源头是线程切换,操作系统做线程切换是依赖 CPU 中断的,所以禁止 CPU 发生中断就能够禁止线程切换。
在早期单核 CPU 时代,这个方案的确是可行的,而且也有很多应用案例,但是并不适合多核场景。
这里我们以 32 位 CPU 上执行 long 型变量的写操作为例来说明这个问题,long 型变量是 64 位,在 32 位 CPU 上执行写操作会被拆分成两次写操作
1 class X { 2 // 修饰非静态方法 3 synchronized void foo() { 4 // 临界区 5 } 6 // 修饰静态方法 7 synchronized static void bar() { 8 // 临界区 9 } 10 // 修饰代码块 11 Object obj = new Object(); 12 void method() { 13 synchronized(obj) { 14 // 临界区 15 } 16 } 17 }
可能你会奇怪,加锁 lock() 和解锁 unlock() 在哪里呢?其实这两个操作都是有的,只是这两个操作是被 Java 默默加上的,Java 编译器会在 synchronized 修饰的方法或代码块前后自动加上加锁 lock() 和解锁 unlock(),这样做的好处就是加锁 lock() 和解锁 unlock() 一定是成对出现的,毕竟忘记解锁 unlock() 可是个致命的 Bug(意味着其他线程只能死等下去了)。
当修饰静态方法的时候,锁定的是当前类的 Class 对象,在上面的例子中就是 Class X;
当修饰非静态方法的时候,锁定的是当前实例对象 this。
锁和受保护资源的关系
标签:str 连续 案例 静态方法 source bsp 之间 使用权 block
原文地址:https://www.cnblogs.com/find-the-right-direction/p/12943856.html