关于互斥锁:html
所谓互斥锁, 指的是一次最多只能有一个线程持有的锁. 在jdk1.5以前, 咱们一般使用synchronized机制控制多个线程对共享资源的访问. 而如今, Lock提供了比synchronized机制更普遍的锁定操做, Lock和synchronized机制的主要区别:java
synchronized机制提供了对与每一个对象相关的隐式监视器锁的访问, 并强制全部锁获取和释放均要出如今一个块结构中, 当获取了多个锁时, 它们必须以相反的顺序释放. synchronized机制对锁的释放是隐式的, 只要线程运行的代码超出了synchronized语句块范围, 锁就会被释放. 而Lock机制必须显式的调用Lock对象的unlock()方法才能释放锁, 这为获取锁和释放锁不出如今同一个块结构中, 以及以更自由的顺序释放锁提供了可能. api
关于可重入: 多线程
1、2.4.1 内部锁线程
Java 提供了原子性的内置锁机制: sychronized 块。它包含两个部分:锁对象的引用和这个锁保护的代码块:htm
synchronized(lock) {对象
// 访问或修改被锁保护的共享状态资源
}get
内部锁扮演了互斥锁( mutual exclusion lock, 也称做 mutex )的角色,一个线程拥有锁的时候,别的线程阻塞等待。同步
2.4.2 重进入(Reentrancy )
重入性:指的是同一个线程屡次试图获取它所占有的锁,请求会成功。当释放锁的时候,直到重入次数清零,锁才释放完毕。
Public class Widget {
Public synchronized void doSomething(){
…
}
}
Public class LoggingWidget extends Widget {
Public synchronized void doSomething(){
System.out.println(toString()+”:calling doSomething”);
Super.doSomething();
}
}
2、通常来讲,在多线程程序中,某个任务在持有某对象的锁后才能运行任务,其余任务只有在该任务释放同一对象锁后才能拥有对象锁,而后执行任务。因而,想到,同一个任务在持有同一个对象的锁后,在不释放锁的状况下,继续调用同一个对象的其余同步(synchronized)方法,该任务是否会再次持有该对象锁呢?
答案是确定的。同一个任务在调用同一个对象上的其余synchronized方法,能够再次得到该对象锁。
Java代码
同一任务和对象锁的问题:http://www.iteye.com/topic/728485
Java代码
一个可重入的互斥锁 Lock,它具备与使用 synchronized 方法和语句所访问的隐式监视器锁相同的一些基本行为和语义,但功能更强大。
ReentrantLock 将由最近成功得到锁,而且尚未释放该锁的线程所拥有。当锁没有被另外一个线程所拥有时,调用 lock 的线程将成功获取该锁并返回。若是当前线程已经拥有该锁,此方法将当即返回。可使用 isHeldByCurrentThread() 和 getHoldCount() 方法来检查此状况是否发生。
此类的构造方法接受一个可选的公平 参数。当设置为 true 时,在多个线程的争用下,这些锁倾向于将访问权授予等待时间最长的线程。不然此锁将没法保证任何特定访问顺序。与采用默认设置(使用不公平锁)相比,使用公平锁的程序在许多线程访问时表现为很低的整体吞吐量(即速度很慢,经常极其慢),可是在得到锁和保证锁分配的均衡性时差别较小。不过要注意的是,公平锁不能保证线程调度的公平性。所以,使用公平锁的众多线程中的一员可能得到多倍的成功机会,这种状况发生在其余活动线程没有被处理而且目前并未持有锁时。还要注意的是,未定时的 tryLock 方法并无使用公平设置。由于即便其余线程正在等待,只要该锁是可用的,此方法就能够得到成功。
JDK:http://www.xasxt.com/java/api/java/util/concurrent/locks/ReentrantLock.html