Java并发-对象锁,类锁

1. Java中加同步锁目前使用synchronized

锁目前可以理解为下面两种锁,然后每种锁都可以加在代码上或者方法上(也可以按照方法锁和代码锁分类)

第一种分类:

1)类锁

A : 只加在某块代码中,但是加锁的是类 synchronized(Sync.class)

b: 加在静态方法上:

public static synchronizedvoid test1() {...}

2)对象锁

A:  加在某块代码中,但是加锁的是对象  

synchronized (this)

B: 加在非静态方法上

public synchronized void test() {...}


第二种分类

1) 方法锁

A: 方法锁锁在非静态方法:即锁在对象

public synchronized void test() {...}

B: 方法锁锁在静态方法上: 即锁在类上

public static synchronized void test1() {...}

2) 代码锁

A:加锁的是类 synchronized(Sync.class)

B: 加在某块代码中,但是加锁的是对象  

synchronized (this)

注意

1)类锁和对象锁不会互斥,不能理解为锁加在类上, 由这个类产生的对象就获取不到锁

2)类锁和类锁互斥,对象锁和同一对象的锁互斥,类锁和对象锁互不排斥,不同对象的锁不互斥

2. 举例

package com.yaya.java.sync;

public class Sync1 {

	public void test() {
		synchronized (Sync1.class) {
			System.out.println("synchronized Sync1.class 开始..");
			try {
				Thread.sleep(2000);
			} catch (InterruptedException e) {
				e.printStackTrace();
			}
			System.out.println("synchronized Sync1.class 结束..");
		}
	}

	public static synchronized void test1() {
		System.out.println("static synchronized void test1 开始..");
		try {
			Thread.sleep(2000);
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
		System.out.println("static synchronized void test1结束..");

	}

	public static void main(String[] args) {
		Sync1 test1 = new Sync1();
		Thread thread = new Thread(new Runnable() {
			public void run() {
				test1.test();
			}
		}, "a");

		Thread thread1 = new Thread(new Runnable() {
			public void run() {
				Sync1.test1();
			}
		}, "b");

		thread1.start();
		thread.start();
	}
}

运行结果

static synchronized void test1 开始..
static synchronized void test1结束..
synchronized Sync1.class 开始..
synchronized Sync1.class 结束..

分析:

synchronized (Sync1. class )  锁在类Sync1上, 

public static synchronizedvoid test1() 也锁在Sync1类上, 所以两个方法互斥。

package com.yaya.java.sync;

public class Sync2 {

	public void test() {
		synchronized (Sync2.class) {
			System.out.println("synchronized (Sync2.class)开始..");
			try {
				Thread.sleep(2000);
			} catch (InterruptedException e) {
				e.printStackTrace();
			}
			System.out.println("synchronized (Sync2.class)结束..");
		}
	}
	
	
	public void test2() {
		synchronized (this) {
			System.out.println("synchronized (this)开始..");
			try {
				Thread.sleep(2000);
			} catch (InterruptedException e) {
				e.printStackTrace();
			}
			System.out.println("synchronized (this)结束..");
		}
	}

	
	public static void main(String[] args)  
    {  
		Sync2 test1 = new Sync2();  
        Thread thread = new Thread(new Runnable()  
        {  
            public void run()  
            {  
                    test1.test();  
            }  
        }, "a");  
        
        Sync2 test2 = new Sync2();  
        Thread thread2 = new Thread(new Runnable()  
        {  
            public void run()  
            {  
 
            	test2.test2();  
 
            }  
        }, "a");  
  
        thread.start();  
        thread2.start();  
    }  
}

运行结果

synchronized (this)开始..
synchronized (Sync2.class)开始..
synchronized (this)结束..
synchronized (Sync2.class)结束..

分析:

类锁和对象锁不互斥

package com.yaya.java.sync;

public class Sync3 {

	public synchronized void test() {
		System.out.println("test开始..");
		try {
			Thread.sleep(2000);
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
		System.out.println("test结束..");
	}
	
	
	public synchronized void test2() {
		System.out.println("test2开始..");
		try {
			Thread.sleep(2000);
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
		System.out.println("test2结束..");
	}

	public static void main(String[] args) {
		Sync3 test1 = new Sync3();
		Thread thread = new Thread(new Runnable() {
			public void run() {
				test1.test();
			}
		}, "a");

		Thread thread2 = new Thread(new Runnable() {
			public void run() {
				test1.test2();
			}
		}, "c");
			
		Sync3 test2 = new Sync3();
		Thread thread3 = new Thread(new Runnable() {
			public void run() {
				test2.test2();
			}
		}, "a");

		thread.start();
		thread2.start();
		thread3.start();
	}
}
运行结果:

test2开始..
test2开始..
test2结束..
test2结束..
test开始..
test结束..

分析:

对象锁,锁同一个对象,会互斥(thread thread2互斥),但是锁的不是同一个对象(thread2 thread3不互斥)

public class Sync4 {

	/**
	 * 加锁方法调用加锁方法
	 */
    private synchronized void testA() {
        System.out.println("testA start");
        testB();
        try {
            Thread.sleep(2000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        System.out.println("testA over");
    }

    private synchronized  void testB() {
        System.out.println("testB start");
        try {
            Thread.sleep(2000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        System.out.println("testB over");
    }

    public static void main(String[] args) {
    	Sync4 syn4 = new Sync4();
    	syn4.testA();
    }
}
运行结果:

testA start
testB start
testB over
testA over
分析:

testA获得了对象锁,虽然testB也需要对象锁,但是运行在testA中, 所以testB也能获得对象锁。


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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值