Come to Java multi-thread design mode
I. Method: Use the Synchronized Method to allow only one pass at a time.
Public Class Userthread Extends Thread { Private Final Gate; Private Final String myname; Private Final String myaddress; Public Userthread (gate, string myname, string myaddress ){ This . Gate = gate;This . Myname = myname; This . Myaddress = myaddress ;} Public Void Run () {system. Out. println (myname +" Begin "); While ( True ) {Gate. Pass (myname, myaddress );}}}
Public Class Gate { Private Int Counter = 0; Private String name =" Nobody "; Private String address =" Nowhere "; Public Void Pass (string name, string address ){ This . Counter ++; This . Name = Name; This . Address = address; check ();} Public String tostring (){ Return " No. "+ Counter +": "+ Name +" , "+ Address ;} Private Void Check (){ If (Name. charat (0 )! = Address. charat (0) {system. Out. println (" * ***** Broken ***** "+ Tostring ());}}}
Only one pass at a time:
Public Class Gate { Private Int Counter = 0; Private String name ="Nobody "; Private String address =" Nowhere "; Public Synchronized VoidPass (string name, string address) { This . Counter ++; This . Name = Name; This . Address = address; check ();} Public SynchronizedString tostring () { Return "No. "+ Counter +" : "+ Name +" , "+ Address ;} Private Void Check (){ If (Name. charat (0 )! = Address. charat (0) {system. Out. println (" * ***** Broken ***** "+ Tostring ());}}}
Ii. making errors more prone: the delay takes up the time in the critical section:
Public Class Gate { Private Int Counter = 0;Private String name =" Nobody "; Private String address =" Nowhere "; Public Void Pass (string name, string address ){ This . Counter ++; This . Name = Name; Try{Thread. Sleep (1000 );}Catch(Interruptedexception e ){} This . Address = address; check ();}Public String tostring (){ Return " No. "+ Counter +" : "+ Name +" , "+ Address ;} Private Void Check (){ If (Name. charat (0 )! = Address. charat (0) {system. Out. println (" * ***** Broken ***** "+ Tostring ());}}}
3. avoid deadlocks:
(1) Multiple shared resources
(2) try to lock another one if the lock is not released
(3) Get a -- get B, or get B -- get a, a/B, with no priority
A deadlock can be avoided if the preceding one is damaged:
Public ClassMain {Public Static VoidMain (string [] ARGs) {system. Out. println ("Testing eaterthread, hit Ctrl + C to exit."); Tool spoon =NewTool ("Spoon"); Tool fork =NewTool ("Fork");NewEaterthread ("Alice", Spoon, fork). Start ();NewEaterthread ("Bobby", Fork, spoon). Start ();}}
Damage (3 ):
Public ClassMain {
Public Static VoidMain (string [] ARGs ){
System. Out. println ("Testing eaterthread, hit Ctrl + C to exit.");
Tool spoon =NewTool ("Spoon");
Tool fork =NewTool ("Fork");
NewEaterthread ("Alice", Spoon, fork). Start ();
NewEaterthread ("Bobby", Spoon, fork). Start ();
}
}
Get spoon first and then get fork.
Damage (1 ):
Change to a shared resource:
Public class main { Public static void main (string [] ARGs) {system. out. println (" testing eaterthread, hit Ctrl + C to exit. "); tool spoon = New tool (" spoon "); tool fork = New tool (" fork "); pair pair = New pair (Spoon, fork); New eaterthread (" Alice ", pair ). start (); New eaterthread (" Bobby ", pair ). start () ;}
Public VoidEat (){Synchronized(Pair) {system. Out. println (name +"Takes up"+ Pair +"."); System. Out. println (name +"Is eating now, yam!"); System. Out. println (name +"Puts down"+ Pair +".");}}