synchronized 类锁 对象锁

分类

类锁:在代码中的方法上加了static和synchronized的锁,或者synchronized(xxx.class)的代码段。

对象锁:在代码中的方法上加了synchronized的锁,或者synchronized(this)的代码段。

代码

package com.example.shengshuqiang.helloworld;

/**
 * User: shengshuqiang
 * Date: 2015-08-31
 * Time: 15:25
 */
public class JavaTest {

    public static void main(String[] args) {
        Object lock = new Object();
        for (int i = 0; i < 5; i++) {
            System.out.println(i);
            new TestClassLockThread().start();
            new TestObjectLockThread().start();
            new TestOneObjectLockThread(lock).start();
        }
    }

    static class A {
        public static synchronized void classLock() {
            System.out.println("classLock start");
            try {
                Thread.sleep(3000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            System.out.println("classLock end");
        }

        public synchronized void objectLock() {
            System.out.println(this + "objectLock start");
            try {
                Thread.sleep(3000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            System.out.println(this + "objectLock end");
        }

        public void oneObjectLock(Object lock) {
            synchronized (lock) {
                System.out.println(this + ", lock= " + lock + ", oneObjectLock start");
                try {
                    Thread.sleep(3000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                System.out.println(this + ", lock= " + lock + ", oneObjectLock end");
            }
        }
    }

    static class TestClassLockThread extends Thread {
        @Override
        public void run() {
            A.classLock();
        }
    }

    static class TestObjectLockThread extends Thread {
        @Override
        public void run() {
            A a = new A();
            a.objectLock();
        }
    }

    static class TestOneObjectLockThread extends Thread {
        private Object lock;
        public TestOneObjectLockThread(Object lock) {
            this.lock = lock;
        }
        @Override
        public void run() {
            A a = new A();
            a.oneObjectLock(lock);
        }
    }
}

输出

0
classLock start
com.example.shengshuqiang.helloworld.JavaTest$A@7461e6f7objectLock start
1
com.example.shengshuqiang.helloworld.JavaTest$A@72116e25, lock= java.lang.Object@7cd68e17, oneObjectLock start
2
com.example.shengshuqiang.helloworld.JavaTest$A@69ab3312objectLock start
3
com.example.shengshuqiang.helloworld.JavaTest$A@47420a89objectLock start
4
com.example.shengshuqiang.helloworld.JavaTest$A@3ff76fb9objectLock start
com.example.shengshuqiang.helloworld.JavaTest$A@20fc4b96objectLock start
classLock end
com.example.shengshuqiang.helloworld.JavaTest$A@72116e25, lock= java.lang.Object@7cd68e17, oneObjectLock end
com.example.shengshuqiang.helloworld.JavaTest$A@7461e6f7objectLock end
com.example.shengshuqiang.helloworld.JavaTest$A@69ab3312objectLock end
com.example.shengshuqiang.helloworld.JavaTest$A@20fc4b96objectLock end
com.example.shengshuqiang.helloworld.JavaTest$A@47420a89objectLock end
com.example.shengshuqiang.helloworld.JavaTest$A@3ff76fb9objectLock end
com.example.shengshuqiang.helloworld.JavaTest$A@615608be, lock= java.lang.Object@7cd68e17, oneObjectLock start
classLock start
classLock end
com.example.shengshuqiang.helloworld.JavaTest$A@615608be, lock= java.lang.Object@7cd68e17, oneObjectLock end
classLock start
com.example.shengshuqiang.helloworld.JavaTest$A@694f64d2, lock= java.lang.Object@7cd68e17, oneObjectLock start
classLock end
com.example.shengshuqiang.helloworld.JavaTest$A@694f64d2, lock= java.lang.Object@7cd68e17, oneObjectLock end
classLock start
com.example.shengshuqiang.helloworld.JavaTest$A@286b2962, lock= java.lang.Object@7cd68e17, oneObjectLock start
classLock end
com.example.shengshuqiang.helloworld.JavaTest$A@286b2962, lock= java.lang.Object@7cd68e17, oneObjectLock end
classLock start
com.example.shengshuqiang.helloworld.JavaTest$A@5922fa5a, lock= java.lang.Object@7cd68e17, oneObjectLock start
classLock end
com.example.shengshuqiang.helloworld.JavaTest$A@5922fa5a, lock= java.lang.Object@7cd68e17, oneObjectLock end

结论

锁的本质是判断是否锁住同一个东西,如果竞争的是同一个锁,则互斥。如果不是同一个锁,则相互不影响。
类锁是锁住该类,全局只有一个类A,所以线程对该类的锁获取是互斥的。一定是先输出“class lock start”,然后“class lock end”,即执行“class lock start”后,别的线程需要等待该方法执行完“class lock end”,才可以接着执行。必须要等到类A的锁释放后才可以重新获取。
对象锁是锁住该对象,
如果竞争的不是同一个对象,则对象锁的获取相互不影响。上面输出可以看出,连续两个 “object lock start”对应的对象this不一样。
如果竞争的是同一个对象,则对象锁的获取互斥。上面输出可以看出,“oneObject lock start”oneObject lock end”顺序出行,在执行“oneObject lock start”后,想要获取该对象锁lock的其他线程必须等待lock锁释放后“oneObject lock end”

参考链接

http://ifeve.com/java-locks/

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值