Java同步:在账户对之间原子转移资金?
如何从一个账户转账到另一个原子账户?对于类:
public class Account {
public Account(BigDecimal initialAmount) {...}
public BigDecimal getAmount() {...}
public void setAmount(BigDecimal amount) {...}
}
我希望以下伪代码:
public boolean transfer(Account from, Account to, BigDecimal amount) {
BigDecimal fromValue = from.getAmount();
if (amount.compareTo(fromValue) < 0)
return false;
BigDecimal toValue = to.getAmount();
from.setAmount(fromValue.add(amount.negate()));
to.setAmount(toValue.add(amount));
return true;
}
在单线程(或顺序)环境中安全地更新帐户。
在多线程/并发环境的情况下,我看到危险情况:
acc1 --> acc2 || acc2 --> acc1
acc1 --> acc2 || acc2 --> acc3 || acc3 --> acc1
...
最简单的解决方案是阻止共享对象,但对于以下情况,这将是低效的:
acc1 --> acc2 || acc3 --> acc4 and acc1 != acc3 and acc2 != acc4
我希望独立传输是并行执行的。
更新似乎建议的解决方案:
synchronize (acc1) {
synchronize (acc2) {
....
}
}
导致死锁,因为2个锁依次获得...
UPDATE 2 “在多线程环境中安全地更新帐户”到底是什么意思?唯一担心的是账户最终不会有零资金还是有其他问题?
如果 and 和我期望一致性:有价值,但没有或 .总数应为 5,而不是 1+3=4 或 4+3=7。acc1(2); acc2(3)
acc1 --1--> acc2
acc2 --2--> acc1
(acc1, acc2)
(3, 2)
(4, 2)
(3, 4)
您一次需要多少并发事务?1000-10000 - 因此锁定共享对象效率不高。