Hidden mutable state and escaped state are two thread insecure issues: the latter is mainly due to the fact that the class member variable contains a reference to other objects, and this reference is immutable, which is the return result type of the Member method that needs attention, will cause thread safety issues
1, about hidden mutable state problem:
Note If the member variable is a reference to another object
The problem is simply that a member variable of a class can be implicitly state, meaning that a member is a reference to an object which is stateful, although the reference may be defined as final immutable but still not thread safe!
First, how can an instance of a class be executed by a multithreaded program?
public class Dateformattest {
The initialization of the member variable is explained here before the constructor!!
Private final DateFormat format =new simpledateformat ("YyyyMMdd");
Public Date convert (String source) throws parseexception{
Date d = format.parse (source);
return D;
}
The}//member variable is immutable, and does not provide a way to change the member, is this object immutable? No, because of the problem of member variable DateFormat
Define an object and then be shared by multithreading
Final Dateformattest t = new dateformattest ();
callable<date> task = new callable<date> () {
Public Date Call () throws Exception {
Return T.convert ("20100811");
}
};
Lets try 2 threads only
Executorservice exec = Executors.newfixedthreadpool (2);
List<future<date>> results =new arraylist<future<date>> ();
Perform 5 date conversions
for (int i = 0; i < 5; i++) {
Results.add (Exec.submit (Task));
}
Exec.shutdown ();
Look at the results
for (future<date> result:results) {
System.out.println (Result.get ());
}
"0.1, the description of this class
This code was not thread safe because simpledateformat.format are not. Is this object immutable? Good question! We have the done we do all fields not modifiable, we don't use any setters or any methods this let us suggest that T He state of the object would change. Actually, internally simpledateformat changes its state, and that's what makes it non-thread safe. Since something changed in the object graph, I would say that it's not immutable, even if it looks like it ...
>>0.2, hidden mutable state problem
SimpleDateFormat
The instance object of this class is saved with intermediate results, so if an instance object is executed by multiple threads, it may confuse each other's execution results. ----The class has member variables
Class SimpleDateFormat
{
Private Calendar
calendar
;
....
public void Parse () {
calendar.clear();//
清空
calendar.add(..);//
填充
}
}
SimpleDateFormat
Stores intermediate results in instance fields. So if one instance are used by and threads they can mess each other's results.
Looking at the source code reveals this there is a Calendar
instance field, which was used by operations on DateFormat
/SimpleDateFormat
For example parse(..)
calls calendar.clear()
initially and then calendar.add(..)
. If another thread invokes parse(..)
before the completion of the first invocation, it'll clear the calendar, but the other I Nvocation would expect it to being populated with (populated) intermediate results of the calculation.
One-to reuse date formats without trading thread-safety are to put them in a ThreadLocal
-some libraries does that. That's if you need the same format multiple times within one thread. If you are using a servlet container (that have a thread pool), remember to clean the thread-local after you Finis H.
>>0.3, solution can do thread local
Another approach is to use a ThreadLocal variable to hold the DateFormat Object,which means so each thread would has its own copy and doesn ' t need to waitfor other threads to release it. This is generally more efficient thansynchronising SA in the previous approach.
public class Dateformattest { private static final threadlocal<dateformat> df = New ThreadLocal< Dateformat> () { @Override protected DateFormat InitialValue () { return new SimpleDateFormat ("YyyyMMdd"); &NBSP;&NBSP;&NBSP;&NBSP;} &NBSP;&NBSP;}; &NBSP; public Date convert (String source) throws parseexception{ date d = df.get (). Parse (source); return D; &NBSP;&NBSP;} |
"2, about escaped state problem:
Notice the return result of the function!!!
Public class Tournament {
Private List<Player> players = new LinkedList<Player> ();
Public synchronized void addplayer (Player p) {
Players.add (P);
}
Public synchronized Iterator<player>getplayeriterator () {
return players.iterator ();
}
For example, all operations of the class member are synchronize methods, the members are mutable, but they are not thread safe!
Consider whether the results returned by each method can still manipulate the mutable state of the Object!
The problem is: The return result of function getplayeriterator () iterator still references the mutable state Containedwithin players-if another thread Calls Addplayer () while the iterator are in use
Two threads are unsafe escaped state and hidden mutable