Synchronized四种作用域:
对象锁:代码块修饰(对象), 非静态函数修饰
类锁: 代码块修饰(类), 静态函数修饰
对象锁:作用域仅限于对应对象内部被synchronized包裹的代码
例子1:对象锁中synchronized 方法
多个线程执行同一个对象的不同加锁非静态方法, 互斥执行
public class SynchronizedExample1 {
private final int loopNum = 5;
// 修饰一个代码块
@SneakyThrows
private void test1(int j) {
synchronized (this) {
for (int i = 0; i < loopNum; i++) {
Thread.sleep(500);
log.info("example:{},current Thread:{}, test1 with sync- {}",j,Thread.currentThread(), i);
}
}
}
// 修饰一个方法
private synchronized void test2(int j) {
for (int i = 0; i < loopNum; i++) {
log.info("test2 {} - {}", i);
}
}
private void test3(int j){
for (int i = 0; i < loopNum; i++) {
log.info("example:{},current Thread:{}, test3 with no sync- {}",j,Thread.currentThread(), i);
}
}
public static void main(String[] args) {
SynchronizedExample1 example1 = new SynchronizedExample1();
SynchronizedExample1 example2 = new SynchronizedExample1();
for(int i=0;i<2;i++){
Thread thread=new Thread(new Runnable() {
@Override
public void run() {
example1.test1(1);
// example1.test3(1);
example2.test1(2);
// example2.test3(2);
}
});
thread.start();
}
}
}
对于对象锁,synchronized作用的对象为SynchronizedExample1的对象实例(比如example1 example2)中被synchronized修饰大括号包裹的代码。
不同线程执行同一个对象example1/example2中对象锁方法互斥执行
不同线程执行不同对象中对象锁方法不互斥
代码中创建三个线程去调用example1和example2中test1方法。example1/example2在三个线程中被调用,输出顺序会被保证,比如example1中三个线程会依次打印。
但是example1 和example2均在多个线程中执行,example1对应test1和example对应test1之间不会保证顺序(注意这里不保证顺序是指exampe1 test1和example2 test1会交替执行,也就是说example1 test1在执行完之前example2 test1也会执行)。从这里可以看出对象锁只能保证该对象对应线程间保证线程安全,不同对象间是不能保证的
执行结果如下
14:09:30.617 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-0,5,main], test1 with sync- 0
14:09:31.131 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-0,5,main], test1 with sync- 1
14:09:31.632 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-0,5,main], test1 with sync- 2
14:09:32.147 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-0,5,main], test1 with sync- 3
14:09:32.662 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-0,5,main], test1 with sync- 4
14:09:33.175 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-0,5,main], test1 with sync- 0
14:09:33.175 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-1,5,main], test1 with sync- 0
14:09:33.676 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-0,5,main], test1 with sync- 1
14:09:33.676 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-1,5,main], test1 with sync- 1
14:09:34.180 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-1,5,main], test1 with sync- 2
14:09:34.180 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-0,5,main], test1 with sync- 2
14:09:34.695 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-1,5,main], test1 with sync- 3
14:09:34.695 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-0,5,main], test1 with sync- 3
14:09:35.209 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-1,5,main], test1 with sync- 4
14:09:35.209 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-0,5,main], test1 with sync- 4
14:09:35.722 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-1,5,main], test1 with sync- 0
14:09:36.236 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-1,5,main], test1 with sync- 1
14:09:36.739 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-1,5,main], test1 with sync- 2
14:09:37.245 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-1,5,main], test1 with sync- 3
14:09:37.758 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-1,5,main], test1 with sync- 4
例子2:对象锁中非synchronized 方法
同一对象加锁方法不影响不加锁的方法
当上边例中
example1.test1(1);
// example1.test3(1);
example2.test1(2);
// example2.test3(2);
改为
// example1.test1(1);
example1.test3(1);
// example2.test1(2);
example2.test3(2);
由于test3没有锁,那么example1内部线程不能保证执行顺序,同时example1 example2之间也不能保证执行顺序
14:21:48.521 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-0,5,main], test3 with no sync- 0
14:21:48.521 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-1,5,main], test3 with no sync- 0
14:21:48.528 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-0,5,main], test3 with no sync- 1
14:21:48.528 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-1,5,main], test3 with no sync- 1
14:21:48.528 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-0,5,main], test3 with no sync- 2
14:21:48.528 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-0,5,main], test3 with no sync- 3
14:21:48.528 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-1,5,main], test3 with no sync- 2
14:21:48.528 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-0,5,main], test3 with no sync- 4
14:21:48.528 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-1,5,main], test3 with no sync- 3
14:21:48.528 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-0,5,main], test3 with no sync- 0
14:21:48.528 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:1,current Thread:Thread[Thread-1,5,main], test3 with no sync- 4
14:21:48.528 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-0,5,main], test3 with no sync- 1
14:21:48.528 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-1,5,main], test3 with no sync- 0
14:21:48.528 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-1,5,main], test3 with no sync- 1
14:21:48.528 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-0,5,main], test3 with no sync- 2
14:21:48.528 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-1,5,main], test3 with no sync- 2
14:21:48.528 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-0,5,main], test3 with no sync- 3
14:21:48.528 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-1,5,main], test3 with no sync- 3
14:21:48.528 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-0,5,main], test3 with no sync- 4
14:21:48.528 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample1 - example:2,current Thread:Thread[Thread-1,5,main], test3 with no sync- 4
类锁:
例子1:类锁中synchronized 方法
不同线程执行同一个对象/多个对象类锁,互斥执行,与对象无关
public class SynchronizedExample2 { private static final int loopNum = 5; // 修饰一个类 private static void test1(int j) { synchronized (SynchronizedExample2.class) { for (int i = 0; i < loopNum; i++) { log.info("example:{},current Thread:{}, test1 with no sync- {}",j,Thread.currentThread(), i); } } } // 修饰一个静态方法 private static synchronized void test2(int j) { for (int i = 0; i < loopNum; i++) { log.info("example:{},current Thread:{}, test2 with no sync- {}",j,Thread.currentThread(), i); } } private static void test3(int j){ for (int i = 0; i < loopNum; i++) { log.info("example:{},current Thread:{}, test3 with no sync- {}",j,Thread.currentThread(), i); } } public static void main(String[] args) { SynchronizedExample2 example1 = new SynchronizedExample2(); SynchronizedExample2 example2 = new SynchronizedExample2(); for(int i=0;i<2;i++){ Thread thread=new Thread(new Runnable() { @Override public void run() { example1.test1(1); // example1.test3(1); example2.test1(2); // example2.test3(2); } }); thread.start(); } } }
类锁锁的作用域是整个class。无论创建多少实例,当其中某一实例调用类中此方法其他实例都要等待持有锁的实例释放锁后才会执行
从输出结果可以看出,example1 example2对应test1方法都是在上个线程释放锁后才执行
输出结果
14:29:59.299 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-0,5,main], test1 with no sync- 0
14:29:59.313 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-0,5,main], test1 with no sync- 1
14:29:59.314 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-0,5,main], test1 with no sync- 2
14:29:59.314 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-0,5,main], test1 with no sync- 3
14:29:59.314 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-0,5,main], test1 with no sync- 4
14:29:59.314 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-0,5,main], test1 with no sync- 0
14:29:59.314 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-0,5,main], test1 with no sync- 1
14:29:59.314 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-0,5,main], test1 with no sync- 2
14:29:59.314 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-0,5,main], test1 with no sync- 3
14:29:59.314 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-0,5,main], test1 with no sync- 4
14:29:59.370 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-1,5,main], test1 with no sync- 0
14:29:59.370 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-1,5,main], test1 with no sync- 1
14:29:59.370 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-1,5,main], test1 with no sync- 2
14:29:59.370 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-1,5,main], test1 with no sync- 3
14:29:59.370 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-1,5,main], test1 with no sync- 4
14:29:59.370 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-1,5,main], test1 with no sync- 0
14:29:59.370 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-1,5,main], test1 with no sync- 1
14:29:59.370 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-1,5,main], test1 with no sync- 2
14:29:59.370 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-1,5,main], test1 with no sync- 3
14:29:59.370 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-1,5,main], test1 with no sync- 4
2 类锁中非synchronized 方法
- 加锁的方法的执行不会影响同一个类/对象中未加锁的方法的执行
public class SynchronizedExample2 { private static final int loopNum = 5; // 修饰一个类 private static void test1(int j) { synchronized (SynchronizedExample2.class) { for (int i = 0; i < loopNum; i++) { log.info("example:{},current Thread:{}, test1 with sync- {}",j,Thread.currentThread(), i); } } for (int i = 0; i < loopNum; i++) { log.info("example:{},current Thread:{}, test1 with no sync- {}",j,Thread.currentThread(), i); } } // 修饰一个静态方法 private static synchronized void test2(int j) { for (int i = 0; i < loopNum; i++) { log.info("example:{},current Thread:{}, test2 with no sync- {}",j,Thread.currentThread(), i); } } public static void main(String[] args) { SynchronizedExample2 example1 = new SynchronizedExample2(); SynchronizedExample2 example2 = new SynchronizedExample2(); for(int i=0;i<2;i++){ Thread thread=new Thread(new Runnable() { @Override public void run() { example1.test1(1); example2.test1(2); } }); thread.start(); } } }
黄色标记部分是不被synchronized包围部分。可见类锁中,sychronzied包裹部分按类锁处理,非synchronized包裹部分没有任何锁行为
14:50:14.651 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-0,5,main], test1 with sync- 0
14:50:14.658 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-0,5,main], test1 with sync- 1
14:50:14.658 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-0,5,main], test1 with sync- 2
14:50:14.658 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-0,5,main], test1 with sync- 3
14:50:14.658 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-0,5,main], test1 with sync- 4
14:50:14.658 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-0,5,main], test1 with no sync- 0
14:50:14.658 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-0,5,main], test1 with no sync- 1
14:50:14.658 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-1,5,main], test1 with sync- 0
14:50:14.659 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-1,5,main], test1 with sync- 1
14:50:14.659 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-0,5,main], test1 with no sync- 2
14:50:14.659 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-1,5,main], test1 with sync- 2
14:50:14.659 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-1,5,main], test1 with sync- 3
14:50:14.659 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-1,5,main], test1 with sync- 4
14:50:14.659 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-1,5,main], test1 with no sync- 0
14:50:14.659 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-0,5,main], test1 with no sync- 3
14:50:14.659 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-1,5,main], test1 with no sync- 1
14:50:14.659 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-1,5,main], test1 with no sync- 2
14:50:14.659 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-0,5,main], test1 with no sync- 4
14:50:14.659 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-0,5,main], test1 with sync- 0
14:50:14.659 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-1,5,main], test1 with no sync- 3
14:50:14.659 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-0,5,main], test1 with sync- 1
14:50:14.659 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:1,current Thread:Thread[Thread-1,5,main], test1 with no sync- 4
14:50:14.659 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-0,5,main], test1 with sync- 2
14:50:14.659 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-0,5,main], test1 with sync- 3
14:50:14.659 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-0,5,main], test1 with sync- 4
14:50:14.659 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-0,5,main], test1 with no sync- 0
14:50:14.659 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-1,5,main], test1 with sync- 0
14:50:14.659 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-0,5,main], test1 with no sync- 1
14:50:14.659 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-1,5,main], test1 with sync- 1
14:50:14.660 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-1,5,main], test1 with sync- 2
14:50:14.660 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-0,5,main], test1 with no sync- 2
14:50:14.660 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-1,5,main], test1 with sync- 3
14:50:14.660 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-1,5,main], test1 with sync- 4
14:50:14.660 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-0,5,main], test1 with no sync- 3
14:50:14.660 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-1,5,main], test1 with no sync- 0
14:50:14.660 [Thread-0] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-0,5,main], test1 with no sync- 4
14:50:14.660 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-1,5,main], test1 with no sync- 1
14:50:14.660 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-1,5,main], test1 with no sync- 2
14:50:14.660 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-1,5,main], test1 with no sync- 3
14:50:14.660 [Thread-1] INFO session.sychronizeDemo.SynchronizedExample2 - example:2,current Thread:Thread[Thread-1,5,main], test1 with no sync- 4
参考文献: https://www.cnblogs.com/jason1990/p/10211640.html
https://www.codeleading.com/article/47494488273/
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· DeepSeek 开源周回顾「GitHub 热点速览」
· 物流快递公司核心技术能力-地址解析分单基础技术分享
· .NET 10首个预览版发布:重大改进与新特性概览!
· AI与.NET技术实操系列(二):开始使用ML.NET
· .NET10 - 预览版1新功能体验(一)