Lock是JDK1.5后提供的对象锁
看一下Lock类的类图
Lock的使用
class MyRunnable implements Runnable {
private int ticket = 100;
private Lock myLock = new ReentrantLock();
@Override
public void run() {
salseTicket();
}
public void salseTicket() {
while (true) {
myLock.lock();
try {
if (ticket > 0) {
try {
Thread.sleep(5);
System.out.println("线程 " + Thread.currentThread().getName() + " sales " + ticket--);
} catch (InterruptedException e) {
e.printStackTrace();
}
} else {
break;
}
} catch (Exception e) {
} finally {
myLock.unlock();
}
}
}
}
Lock对象必须手动加锁,和手动释放锁
synchronized是java中的一个关键字,也就是说是Java语言内置的特性。那么为什么会出现Lock呢?
如果一个代码块被synchronized修饰了,当一个线程获取了对应的锁,并执行该代码块时,其他线程便只能一直等待,等待获取锁的线程释放锁,而这里获取锁的线程释放锁会有三种情况:
1)获取锁的线程执行完了该代码块,然后线程释放对锁的占有;
2)线程执行发生异常,此时JVM会让线程自动释放锁。
3)这个主要是在等待唤醒机制里面的wait()方法,//在等待的时候立即释放锁,方便其他的线程使用锁。而且被唤醒时,就在此处唤醒,
那么如果这个获取锁的线程由于要等待IO或者其他原因(比如调用sleep方法)被阻塞了,但是又没有释放锁,其他线程便只能干巴巴地等待,试想一下,这多么影响程序执行效率。因此我们需要不论程序的代码块执行的如何最终都将锁对象进行释放,方便其他线程的执行。