Java 锁Lock实例使用

Java 锁Lock实例使用

synchronized和Lock区别:
synchronized:

(如果一个代码块被synchronized修饰了,当一个线程获取了对应的锁,并执行该代码块时,其他线程便只能一直等待,等待获取锁的线程释放锁)
获取锁的线程释放锁情况:

1、获取锁的线程执行完了该代码块,然后线程释放对锁的占有。

2、线程执行发生异常,此时JVM会让线程自动释放锁。

3、这个主要是在等待唤醒机制里面的wait()方法,在等待的时候立即释放锁,方便其他的线程使用锁。而且被唤醒时,就在此处唤醒。

虽然我们可以理解同步代码块和同步方法的锁对象问题,但是我们并没有直接看到在哪里加上了锁,在哪里释放了锁,同时为了更好地释放锁。
锁对象Lock:

(通过Lock可以知道线程有没有成功获取到锁。这个是synchronized无法办到的)

1、Lock不是Java语言内置的,synchronized是Java语言的关键字,因此是内置特性。Lock是一个类,通过这个类可以实现同步访问。

2、synchronized是在JVM层面上实现的,不但可以通过一些监控工具监控synchronized的锁定,而且在代码执行时出现异常,JVM会自动释放锁定,但是使用Lock则不行,lock是通过代码实现的,要保证锁定一定会被释放,就必须将unLock()放到finally{}中。

3、在资源竞争不是很激烈的情况下,synchronized的性能要优于ReetrantLock,但是在资源竞争很激烈的情况下,synchronized的性能会下降几十倍。
Lock使用简单示例:(卖火车票例子)

package code;

import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

/**
 *
 * sellTicket.java
 * @author 董欣欣
 * @date 2017年4月9日 上午8:55:04
 */
public class sellTicket implements Runnable{

    private static int num=30;
    private Lock lock=new ReentrantLock();
    @Override
    public void run() {
        // TODO Auto-generated method stub
        while(num>0){
            try{
                lock.lock();
                if(num>0){
                    try {
                        Thread.sleep(500);
                    } catch (InterruptedException e) {
                        // TODO Auto-generated catch block
                        e.printStackTrace();
                    }
                    System.out.println(Thread.currentThread().getName()+"正在出售"+num--);
                }
            }finally{
                lock.unlock();
            }
        }
    }
}

    
 

package code;
 
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;
 
/**
 *
 * sellTicket.java
 * @author 董欣欣
 * @date 2017年4月9日 上午8:55:04
 */
public class sellTicket implements Runnable{
 
    private static int num=30;
    private Lock lock=new ReentrantLock();
    @Override
    public void run() {
        // TODO Auto-generated method stub
        while(num>0){
            try{
                lock.lock();
                if(num>0){
                    try {
                        Thread.sleep(500);
                    } catch (InterruptedException e) {
                        // TODO Auto-generated catch block
                        e.printStackTrace();
                    }
                    System.out.println(Thread.currentThread().getName()+"正在出售"+num--);
                }
            }finally{
                lock.unlock();
            }
        }
    }
}

测试方法:
 

public static void main(String args[]) {
        sellTicket str = new sellTicket();
        Thread tr1 = new Thread(str, "窗口1");
        Thread tr2 = new Thread(str, "窗口2");
        Thread tr3 = new Thread(str, "窗口3");
        tr1.start();
        tr2.start();
        tr3.start();
    }

    
public static void main(String args[]) {
        sellTicket str = new sellTicket();
        Thread tr1 = new Thread(str, "窗口1");
        Thread tr2 = new Thread(str, "窗口2");
        Thread tr3 = new Thread(str, "窗口3");
        tr1.start();
        tr2.start();
        tr3.start();
    }

猜你喜欢

转载自blog.csdn.net/yucaifu1989/article/details/107960979
今日推荐