Java thread synchronization critical section: thinking in java4 21.3.5, java421.3.5
Java thread synchronization critical section: thinking in java4 21.3.5
Thinking in java 4 free download: http://download.csdn.net/detail/liangrui1988/7580155
Package org. rui. thread. critical; import java. util. arrayList; import java. util. collections; import java. util. list; import java. util. concurrent. executorService; import java. util. concurrent. executors; import java. util. concurrent. timeUnit; import java. util. concurrent. atomic. atomicInteger;/The *** critical section *** Pair is NOT thread-safe, because its constraints (although arbitrary) require the two variables to be maintained to the same value. * In addition, as described earlier in this chapter, auto-increment operations are not thread-safe. * because no method is marked as synchronized, a pair object cannot be destroyed in a multi-threaded program. * @ author lenovo ** // org. rui. thread. critical. criticalSection. javaclass Pair {private int x, y; public Pair (int x, int y) {this. x = x; this. y = y;} public Pair () {this (0, 0);} public int getX () {return x;} public int getY () {return y ;} public void incrementX () {x ++;} public void incrementY () {y ++;} public String toString () {return" X: "+ x +", y: "+ y ;} ///////////// PariValuesNotEqualExceptionpublic class PariValuesNotEqualException extends RuntimeException {public PariValuesNotEqualException () {super ("Pair values not equal:" + Pair. this) ;}}// any change. The two variables must be equal. // Arbitrary invariant -- both variables must be equal: public void checkState () {if (x! = Y) {throw new PariValuesNotEqualException () ;}}// Pair end // protection of a pair of classes that are secure in one thread // protect a Pair inside a thread-safe class: abstract class PairManager {AtomicInteger checkCounter = new AtomicInteger (0); protected Pair p = new Pair (); private List <Pair> storage = Collections. synchronizedList (new ArrayList <Pair> (); public synchronized Pair getPair () {// original replication security: // Make a copy to keep the original safe: return new Pair (p. getX (), p. getY ();} // Assume this is a time-consuming operation // Assume this is a time consuming operation protected void store (Pair p) {storage. add (p); try {TimeUnit. MILLISECONDS. sleep (50);} catch (InterruptedException e) {e. printStackTrace () ;}// public abstract void increment ();} // the entire synchronization method // synchronize the entire methodclass PairManager1 extends PairManager {@ Overridepublic synchronized void increment () {p. incrementX (); p. incrementY (); store (getPair () ;}// use a critical section: use the critical section class PairManager2 extends PairManager {public void increment () {Pair temp; synchronized (this) {p. incrementX (); p. incrementY (); temp = getPair ();} store (temp) ;}/// operator class PairManipulator implements Runnable {private PairManager pm; public PairManipulator (PairManager pm) {this. pm = pm ;}@ Overridepublic void run () {while (true) pm. increment ();} public String toString () {return "Pair:" + pm. getPair () + "checkCounter =" + pm. checkCounter. get () ;}/// PairCheckerclass PairChecker implements Runnable {private PairManager pm; public PairChecker (PairManager pm) {this. pm = pm ;}@ Overridepublic void run () {while (true) {pm. checkCounter. incrementAndGet (); pm. getPair (). checkState ();}}} //////////////////////////////////////// ///////////// public class CriticalSection {// test two different methods // test the two defferent approachesstatic void testApproaches (PairManager pman1, pairManager pman2) {ExecutorService exec = Executors. newCachedThreadPool (); PairManipulator pm1 = new PairManipulator (pman1); PairManipulator pm2 = new worker (pman2); PairChecker pcheck1 = new PairChecker (pman1 ); pairChecker pcheck2 = new PairChecker(pman2);exec.execute(pm1);exec.execute(pm2);exec.execute(pcheck1);exec.exe cute (pcheck2); try {TimeUnit. MILLISECONDS. sleep (500);} catch (InterruptedException e) {System. out. println ("InterruptedException");} System. out. println ("pm1:" + pm1 + "\ npm2:" + pm2); System. exit (0);} public static void main (String [] args) {PairManager pman1 = new PairManager1 (), pman2 = new PairManager2 (); testApproaches (pman1, pman2) ;}}/** output :( sample) pm1: Pair: x: 8, y: 8 checkCounter = 671_7pm2: Pair: x: 8, y: 8 checkcounter= 5043736 */
Package org. rui. thread. critical; import java. util. concurrent. locks. lock; import java. util. concurrent. locks. reentrantLock;/*** you can also use the displayed lock Object to create a critical section. ** CriticalSection is used here. the vast majority of java, * and create a new PairManger type that uses explicit lock objects. * ExpliciPariManger2 shows how to use a Lock object to create a critical section () * @ author lenovo **////////////////////////// /class ExplicitPairManager1 extends PairManager {private Lock lock = new ReentrantLock (); @ Overridepublic synchronized void increment () {lock. lock (); try {p. incrementX (); p. incrementY (); store (getPair ();} finally {lock. unlock () ;}}// use a critical sectionclass ExplicitPairManager2 extends PairManager {private Lock lock = new ReentrantLock (); @ Overridepublic void increment () {Pair temp = null; lock. lock (); try {p. incrementX (); p. incrementY (); temp = getPair ();} finally {lock. unlock () ;}store (temp );}} ////////////// public class ExplicitCriticalSection {public static void main (String [] args) {PairManager pman1 = new PairManager1 (), pman2 = new PairManager2 (); CriticalSection. testApproaches (pman1, pman2) ;}/ *** output: pm1: Pair: x: 10, y: 10 checkCounter = 195142pm2: Pair: x: 11, y: 11 checkcounter= 4129459 */
How does a java thread protect critical zones?
The program that accesses Critical resources in each process is called a Critical Section (a Critical resource is a shared resource that can only be used by one process at a time ). Only one process can enter the critical section at a time. Other processes are not allowed to enter the critical section. Whether it is a hardware critical resource or a software critical resource, multiple processes must access it with mutual exclusion. Critical zones involving the same critical resource in multiple processes are called related critical zones. The scheduling principle for a process to enter the critical section is as follows: ① if several processes require to enter the idle critical section, only one process can be entered at a time. ② At any time, there must be no more than one process in the critical section. If a process has entered its own critical section, all other processes that attempt to enter the critical section must wait. ③ Processes entering the critical section should exit within a limited period of time so that other processes can enter their critical section in time. ④ If a process cannot enter its critical section, the CPU should be used out to avoid the process being "busy. If multiple threads attempt to access the critical section at the same time, all other threads attempting to access the critical section will be suspended and will continue until the thread enters the critical section. After the critical section is released, other threads can continue to seize it and use the atomic method to share resources.
In java, how does one use the synchronized critical section?
Four synchronized usage
1. used for method declaration, placed after the range operator (public, etc.), before the return type declaration (void, etc. that is, only one thread can enter this method at a time. If other threads want to call this method at this time, they can only wait in queue. After the current thread (that is, the thread inside the synchronized Method) executes this method, other threads can enter.
For example:
Public synchronized void synMethod (){
// Method body
}
2. For a code block, synchronized is followed by parentheses and contains variables. In this way, only one thread enters the code block at a time. For example:
Public int synMethod (int a1 ){
Synchronized (a1 ){
// Only one thread can enter
}
}
3. synchronized is followed by an object in parentheses. At this time, the thread obtains an object lock. For example:
Public class MyThread implements Runnable {
Public static void main (String args []) {
MyThread mt = new MyThread ();
Thread t1 = new Thread (mt, "t1 ");
Thread t2 = new Thread (mt, "t2 ");
Thread t3 = new Thread (mt, "t3 ");
Thread t4 = new Thread (mt, "t4 ");
Thread t5 = new Thread (mt, "t5 ");
Thread t6 = new Thread (mt, "t6 ");
T1.start ();
T2.start ();
T3.start ();
T4.start ();
T5.start ();
T6.start ();
}
Public void run (){
Synchronized (this ){
System. out. println (Thread. currentThread (). getName ());
}
}
}
For 3, if the thread enters, the object lock will be obtained, and no operations can be performed by other threads on all objects of this class. locking at the object level is usually a rough method. Why is it necessary to lock the entire object and not allow other threads to temporarily use other Synchronization Methods in the object to access Shared resources? If an object has multiple resources, you do not need to lock all threads out to allow a thread to use some of the resources. Because each object has a lock, you can use a virtual object to lock it as follows:
Class FineGrainLock {
MyMemberClass x, y;
Object xlock = new Object (), ylock = new Object ();
Public void foo (){
Synchronized (xlock ){
// Access x here
}
// Do something here-but don't use shared resources
Synchronized (ylock ){
// Access y here
}
}
Public void bar (){
Synchronized (this ){
// Access both x... the remaining full text>