Reputation: 1870
I was recently going through "Java Concurrency in practice" and came across example of Publication and Escape , after going through it several times I still feel that I didn't completely understood the example.
public class ThisEscape{
public ThisEscape(EventSource source){
source.registerListener(
new EventListener(){
public void onEvent(Event e){
doSomething(e);
}
}
)
}
}
ThisEscape illustrates an important special case of Escape - when the this references escapes during construction. When the inner EvenListener instance is publised ,so is the enclosing ThisEsape instance.But and object is in a predictable ,consistent state only after its constructuor return. so publishing an object from within its constructor can publish an incompletely constructed object.This is true even if the publication is the last statement in the constructor.If the this reference escapes during construction, the object is considered not properly constructed.
ThisEscape
cosntructor is registering a EventSource with and EventListener where we are specifying an onEvent behaviour passing an Event instance.
But here I assume the order of object construction to be EventListener --> ThisEscape
so how the this reference of ThisEscape
is being passed here to escape ?
Upvotes: 0
Views: 342
Reputation: 111
Actually it requires registering events after completing initialisation of objects (after construction) so it recommends use private construction
private SafeListener(){
listener = new EventListener(){
public void onEvent(Event e){
doSomething(e);
}
};
}
public static SafeListener newInstance(EventSource source){
SafeListener safe = new SafeListener();
source.registerListener(safe.listener);
return safe;
}
this one is much safer.
Upvotes: 0
Reputation: 4799
I believe we should refer to this excerpt:
When the inner EvenListener instance is published, so is the enclosing ThisEsape instance.
Which makes me think doSomething()
is a method of ThisEscape
(otherwise the reference would not escape), meaning ThisEscape
is a listener for EventSource
, and it registers itself during construction via overriding EventListener
's onEvent
method.
In simple words, it says: "when a new event occurs, call doSomething()
".
At this point the problem is quite simple. Imagine it, we've registered a new listener inside ThisEscape
's constructor... and immediately... an event occurs! While one thread is still constructing ThisEscape
, another one is already calling doSomething()
, which may lead to a very unpredictable result...
Upvotes: 1