假设有以下 Account 类的两个对象 - account1 和 account2。并且有两个线程T1和T2。
T1 正在将金额 100 从 account1 转移到 account2,如下所示:
account1.transfer(account2, 100);
同样,T2 将金额 50 从 account2 转移到 account1:
account2.transfer(account1, 50);
transfer() 方法显然容易出现死锁,因为两个线程 T1 和 T2 会尝试以相反的顺序获取锁。(线程 T1 将首先尝试获取 account1 的锁,然后是 account2。而线程 T2 将尝试获取 account2 的锁,然后是 account1。)
确保始终保证锁定顺序的最佳方法是什么(在这种情况下)?
public class Account {
private float balance;
public class Account() {
balance = 5000f;
}
private void credit(float amt) {
balance += amt;
}
// To exclude noise assume the balance will never be negative
private void debit(float amt) {
balance -= amt;
}
// Deadlock prone as the locking order is not guaranteed
public void transfer(Account acc2, float amt) {
synchronized(this) {
synchronized(acc2) {
acc2.debit(amt);
this.credit(amt);
}
}
}
}