码迷,mamicode.com
首页 > 其他好文 > 详细

synchronized锁

时间:2020-01-07 13:17:22      阅读:84      评论:0      收藏:0      [点我收藏+]

标签:art   system   选择   rac   pre   共存   其他   sys   test   

基础知识:
每一个对象都有一个监听器(monitor)且只有一个

synchronized锁可分为对象锁和静态锁, 顾名思义对象锁就是给实例对象进行加锁, 静态锁则是给类进行加锁

举个例子:好比上厕所, 第一个人进厕所后把厕所门锁住,后面的人就只能排队进等待, 直到前面一个人把厕所门打开

 

synchronized常见方式如下:

1 对象方法加锁(对象锁)

public synchronized void test(){
        //doSomething。。。。。
}  

2 静态方法加锁(静态锁)

public synchronized static void test(){
        //doSomething。。。。。
}

3 对象加锁(对象锁)

Object object = new Object();
public void test(){
    synchronized (object){
      //doSomeing。。。。
    }
}

4 方法中给类加锁(静态锁)

public void test(){
      synchronized (SocketServerTest.class){
          //doSomeing。。。。
      }
}

 

思考:

对象锁锁住对象, 若其他方法块需要获取当前对象锁则必须排队等待释放;  静态锁(也称为类锁)则是在使用类加锁或静态方法加锁时需要排队

那么问题来了若类锁和对象锁共存是一种什么样的情况呢, 我们给静态方法和普通方法都加上锁

 

对于以下代码我们可以预测可能会有两种情况

1对象锁和类锁为互斥, 需要排队 预测结果 test1 test2 tStatic1 tStatic2

2对象锁和类锁无关联,各自作用域不同 预测结果  tStatic1 tStatic2  test1 test2


public static void main(String[] args) throws InterruptedException {
Test test = new Test();
Thread t1 = new Thread(()->test.test1());
Thread t2 = new Thread(()->test.test2());
Thread tStatic1 = new Thread(()->Test.testStatic1());
Thread tStatic2 = new Thread(()->Test.testStatic2());
t1.start();
   //保证t2在t1之后获取锁
Thread.sleep(300);
t2.start();
//保证tStatic1在t2之后获取锁
Thread.sleep(300);
tStatic1.start();
//保证tStatic2在tStatic1之后获取锁
Thread.sleep(300);
tStatic2.start();
}


public static class Test{

public synchronized void test1() {
//休眠5秒
try {
Thread.sleep(5*1000);
}catch (Exception e){
e.printStackTrace();
}
System.out.println("test1");
}

public void test2() {
synchronized (this){
System.out.println("test2");
}
}

public synchronized static void testStatic1(){
//休眠3秒
try {
Thread.sleep(3*1000);
}catch (Exception e){
e.printStackTrace();
}
System.out.println("testStatic1");
}

public static void testStatic2(){
synchronized (Test.class){
System.out.println("testStatic2");
}
}
}


打印结果:

testStatic1
testStatic2
test1
test2

从以上结果可以看出,对象锁和类锁完全互不影响

那么回到上面上厕所的例子, 那么对象锁和类锁就意味着互不影响的两个厕所门,做个简单命名对象厕所, 类厕所,  选择上对象厕所的人需要等待前面对象厕所的人出来, 同理等待类厕所的人也一样要等待前面的人出来

 

通常情况下挺合情合理, 但是如果厕所里面有洗手台,有蹲坑, 那么对于只想洗手的人而言显然就不合理了, 洗手只要十几秒而且人很多, 真正上厕所的人少而且时间特别长,显然synchronized很有局限性无法解决这个问题, 就需要使用到读写锁

synchronized锁

标签:art   system   选择   rac   pre   共存   其他   sys   test   

原文地址:https://www.cnblogs.com/xieyanke/p/12160764.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!