为什么"Java Concurrency in Practice Listing 10.5."可以生成完整的快照?



我正在阅读Java并发实践,并遇到以下代码片段。

// Listing 10.5. Lock-ordering deadlock between cooperating objects. Don’t do this.
import java.util.HashSet;
import java.util.Set;
// Warning: deadlock-prone!
class Taxi {
@GuardedBy("this")
private Point location, destination;
private final Dispatcher dispatcher;
public Taxi(Dispatcher dispatcher) {
this.dispatcher = dispatcher;
}
public synchronized Point getLocation() {
return location;
}
public synchronized void setLocation(Point location) {
this.location = location;
if (location.equals(destination))
dispatcher.notifyAvailable(this);
}
}
class Dispatcher {
@GuardedBy("this")
private final Set<Taxi> taxis;
@GuardedBy("this")
private final Set<Taxi> availableTaxis;
public Dispatcher() {
taxis = new HashSet<Taxi>();
availableTaxis = new HashSet<Taxi>();
}
public synchronized void notifyAvailable(Taxi taxi) {
availableTaxis.add(taxi);
}
public synchronized Image getImage() {
Image image = new Image();
for (Taxi t : taxis)
image.drawMarker(t.getLocation());
return image;
}
}

然后它说:

在容易死锁的版本中,getImage 会生成该时刻队列位置的完整快照。

调用getImage时,我们得到了 Dispatcher 的内在锁,其他线程不能修改taxis其他线程仍然可以修改Taxilocation,尽管调用getImage的线程可能看不到更改。那么,为什么getImage可以在那一刻生成车队位置的完整快照呢?

调用getImage的线程将看到位置更改。当我读到时

在该时刻生成快照位置的完整快照

我将其解释为从getImage开始执行出租车的位置就无法更改,但它们可以通过Taxi中的setLocation调用来更改,并且这些更改将是可见

的。

最新更新