【发布时间】:2021-07-04 21:23:54
【问题描述】:
我正在阅读以下关于为什么不推荐客户端锁定的部分:
“有时,程序员使用对象的锁来实现附加
原子操作——一种称为客户端锁定的做法。考虑一下,对于
例如 Vector 类,它是一个方法同步的列表。
现在假设我们将银行余额存储在 Vector 中。这里是
传输方法的幼稚实现:
public void transfer(Vector accounts, int from, int to, int amount) //
{
accounts.set(from, accounts.get(from) - 金额);
accounts.set(to, accounts.get(to) + amount);
System.out.println(. . .);
}
Vector类的get和set方法是同步的,但是那个
对我们没有帮助。线程完全有可能在
中被抢占
第一次调用 get 完成后的 transfer 方法。另一个
然后线程可以将不同的值存储到相同的位置。但是,我们
可以劫持锁:
公共无效转移(向量帐户,int from,int to,int amount)
{
同步(帐户)
{
accounts.set(from, accounts.get(from) - 金额);
accounts.set(to, accounts.get(to) + amount);
}
System.out.println(. . .);
}
这种方法有效,但它完全取决于 Vector
类对其所有的 mutator 方法使用内部锁。但是,这是
真的是事实吗? Vector 类的文档没有这样的
承诺。你要仔细研究源代码,希望以后
版本不引入不同步的变异器。如您所见,客户端-
侧锁非常脆弱,一般不推荐。”
问题:
既然transfer方法中的synchronized(accounts)已经获得了accounts的内在锁,为什么依赖vector类的所有mutator方法都使用了内在锁(以粗斜体突出显示?
【问题讨论】:
-
向量集(mutator)方法看源码是同步的..
-
为什么会被选为-1?