同步會導(dǎo)致另一個可能的問題就是死鎖(deadlock)型檀。如果兩個線程需要獨占訪問統(tǒng)一的一個資源集听盖,而每個線程分別有這些資源的不同子集鎖,就會發(fā)生死鎖仓坞。如果兩個線程都不愿意放棄已經(jīng)擁有的資源腰吟,就會進入無限停止?fàn)顟B(tài)。
下面是一個簡單的死鎖例子
public classDeadLock {
public static final Stringres1="res1";
public static final Stringres2="res2";
public static void main(String[] args) {
Thread lock1 = new Thread(new Lock1());
lock1.start();
Thread lock2 = new Thread(new Lock2());
lock2.start();
}
static class Lock1 implements Runnable {
@Override
public void run() {
synchronized(DeadLock.res1) {
System.out.println("thread-1 locked res1");
try{
Thread.sleep(300);
synchronized(DeadLock.res2) {
System.out.println("thread-1 locked res2");
}
}catch(InterruptedException e) {
e.printStackTrace();
}
}
}
}
static class Lock2 implements Runnable {
@Override
public void run() {
synchronized(DeadLock.res2) {
System.out.println("thread-2 locked res2");
try{
Thread.sleep(300);
synchronized(DeadLock.res1) {
System.out.println("thread-2 locked res1");
}
}catch(InterruptedException e) {
e.printStackTrace();
}
}
}
}
}
要防止死鎖嫉称,最重要的技術(shù)是避免不必要的同步灵疮。如果有其它方法可以確保線程安全,比如讓對象不可變或保存對象的一個局部副本荔棉。如果確實要使用同步,要保持同步塊盡可能小润樱,而且盡量不要一次同步多個對象。