Does happens before Program order rule work in constructors?
Is it really possible to view partially constructed object in the thread created in the constructor because of the lack of synchronization and the leaking this instance?
Except for the case when there is a child class, of course, or we are doing implicit construction with clone or something like that - so let's suppose that the class is final and is it's fully initialized in the thread calling the constructor before calling other thread.
As I understand the following hb() rules apply,
Each action in a thread happens-before every action in that thread that comes later in the program order (Program Order Rule)
A call to start() on a thread happens-before any actions in the started thread.
If hb(x, y) and hb(y, z), then hb(x, z)
So does it mean that the following code is technically thread safe(I have taken it from the similar question Why shouldn't I use Thread.start() in the constructor of my class?, there is also a similar question Why it is bad practice to create a new thread on constructors?, ps I hope this one won't be closed as duplicate)
final class SomeClass
{
public ImportantData data = null;
public Thread t = null;
public SomeClass(ImportantData d)
{
t = new MyOperationThread();
// t.start(); // Footnote 1
data = d;
t.start(); // Footnote 2
}
}
PS obviously data field lacks encapsulation here, however this question is about the object's state visibility from thread t.
Yes, it does. The spec clearly writes:
An action that starts a thread synchronizes-with the first action in the thread it starts.
Of course, an object is not guaranteed to be fully initialized when a constructor completes, because constructors can invoke other constructors - either through an explicit constructor invocation statement, or because a superclass default constructor is implicitly called. Therefore, leaking this
from a constructor is rather fragile - with a single or multiple threads.
上一篇: 可本地化的xcassets文件?