ThreadStart method to achieve multi-threading

Multithreading with ThreadStart

3.1 Using the ThreadStart delegate

Here is an example to demonstrate the benefits of multi-threading. First, a method ShowMessage() is established in the Message class, which displays the ID of the currently running thread, and uses the Thread.Sleep(int) method to simulate part of the work. Bind the ShowMessage() method of the Message object through the ThreadStart delegate in main(), and then execute the asynchronous method through Thread.Start().

1       public class Message
 2       {
 3           public void ShowMessage()
 4           {
 5               string message = string.Format("Async threadId is :{0}",
 6                                               Thread.CurrentThread.ManagedThreadId);
 7               Console.WriteLine(message);
 8   
 9               for (int n = 0; n < 10; n++)
10               {
11                   Thread.Sleep(300);   
12                   Console.WriteLine("The number is:" + n.ToString());
13               }
14           }
15       }
16   
17       class Program
18       {
19           static void Main(string[] args)
20           {
21               Console.WriteLine("Main threadId is:"+
22                                 Thread.CurrentThread.ManagedThreadId);
23               Message message=new Message();
24               Thread thread = new Thread(new ThreadStart(message.ShowMessage));
25               thread.Start();
26               Console.WriteLine("Do something ..........!");
27               Console.WriteLine("Main thread working is complete!");
28               
29           }
30       }
Please pay attention to the running result. After calling the Thread.Start() method, the system runs Message.ShowMessage() asynchronously, while the operation of the main thread continues. Before Message.ShowMessage() is completed, the main thread has completed all operation.

 

3.2 Using the ParameterizedThreadStart delegate

The ParameterizedThreadStart delegate is very similar to the ThreadStart delegate, but the ParameterizedThreadStart delegate is for methods with parameters. Note that the parameter of the corresponding method of ParameterizedThreadStart is object, which can be a value object or a custom object.

1     public class Person
 2     {
 3         public string Name
 4         {
 5             get;
 6             set;
 7         }
 8         public int Age
 9         {
10             get;
11             set;
12         }
13     }
14
15     public class Message
16     {
17         public void ShowMessage(object person)
18         {
19             if (person != null)
20             {
21                 Person _person = (Person)person;
22                 string message = string.Format("\n{0}'s age is {1}!\nAsync threadId is:{2}",
23                     _person.Name,_person.Age,Thread.CurrentThread.ManagedThreadId);
24                 Console.WriteLine(message);
25             }
26             for (int n = 0; n < 10; n++)
27             {
28                 Thread.Sleep(300);   
29                 Console.WriteLine("The number is:" + n.ToString());
30             }
31         }
32     }
33
34     class Program
35     {
36         static void Main(string[] args)
37         {     
38             Console.WriteLine("Main threadId is:"+Thread.CurrentThread.ManagedThreadId);
39             
40             Message message=new Message();
41 //Bind an asynchronous method with parameters 
42 Thread thread = new Thread(new ParameterizedThreadStart(message.ShowMessage)); 43 Person person = new Person(); 44 person.Name = "Jack"; 45 person.Age = 21; 46 thread.Start(person); //Start asynchronous thread
47 48 Console.WriteLine("Do something ..........!"); 49 Console.WriteLine("Main thread working is complete!"); 50 51 } 52 }
operation result:

 

3.3 Foreground threads and background threads

Note that the above two examples do not use Console.ReadKey(), but the system will still wait for the asynchronous thread to complete before ending. This is because the thread started with Thread.Start() is the foreground thread by default, and the system must wait for all foreground threads to finish running before the application domain is automatically unloaded.

In the second section, it was introduced that the thread Thread has an attribute IsBackground. By setting this attribute to true, the thread can be set as a background thread! In this case the application domain will be unloaded when the main thread completes, without waiting for the asynchronous thread to run.

 

3.4 Suspend a thread

To wait for other background threads to finish before ending the main thread, use the Thread.Sleep() method.

1     public class Message
 2     {
 3         public void ShowMessage()
 4         {
 5             string message = string.Format("\nAsync threadId is:{0}",
 6                                            Thread.CurrentThread.ManagedThreadId);
 7             Console.WriteLine(message);
 8             for (int n = 0; n < 10; n++)
 9             {
10                 Thread.Sleep(300);
11                 Console.WriteLine("The number is:" + n.ToString());
12             }
13         }
14     }
15
16     class Program
17     {
18         static void Main(string[] args)
19         {     
20             Console.WriteLine("Main threadId is:"+
21                               Thread.CurrentThread.ManagedThreadId);
22             
23             Message message=new Message();
24             Thread thread = new Thread(new ThreadStart(message.ShowMessage));
25             thread.IsBackground = true;
26             thread.Start();
27             
28             Console.WriteLine("Do something ..........!");
29             Console.WriteLine("Main thread working is complete!");
30             Console.WriteLine("Main thread sleep!");
31             Thread.Sleep(5000);
32         }
33     }

The running result is as follows, at this time, the application domain will automatically end after the main thread runs for 5 seconds

But the system cannot predict how long the asynchronous thread needs to run, so blocking the main thread with Thread.Sleep(int) is not a good solution. With this in mind, .NET has developed another method thread.Join() specifically for waiting for an asynchronous thread to complete. Modifying the last line of Thread.Sleep (5000) in the above example to thread.Join() ensures that the main thread will not terminate until the asynchronous thread thread finishes running.

 

3.5 Suspend and Resume (use with caution)

Thread.Suspend() and Thread.Resume() are old methods that existed in Framework1.0, they can suspend and resume threads respectively. However, these two methods have been explicitly excluded in Framework2.0. This is because once a thread occupies an existing resource and uses Suspend() to keep the thread in a suspended state for a long time, it will cause deadlock when other threads call these resources! So these two methods should be avoided unless necessary.

 

3.6 Terminate the thread

To terminate a running thread, use the Abort() method. When using Abort(), a special exception ThreadAbortException is thrown.
If you want to resume the execution of the thread before the thread is terminated, you can call Thread.ResetAbort() in catch(ThreadAbortException ex){...} after catching the exception to cancel the termination.
Using Thread.Join() can ensure that the application domain waits for the asynchronous thread to end before terminating the operation.

1          static void Main(string[] args)
 2          {
 3              Console.WriteLine("Main threadId is:" +
 4                                Thread.CurrentThread.ManagedThreadId);
 5  
 6              Thread thread = new Thread(new ThreadStart(AsyncThread));
 7              thread.IsBackground = true;
 8              thread.Start();
 9              thread.Join();
10  
11          }     
12          
13 //Call 
14 asynchronously static void AsyncThread() 15 { 16 try 17 { 18 string message = string.Format("\nAsync threadId is:{0}", 19 Thread.CurrentThread.ManagedThreadId); 20 Console.WriteLine(message); 21 22 for (int n = 0; n < 10; n++) 23 { 24 //When n is equal to 4, terminate the thread
25 if (n >= 4) 26 { 27 Thread.CurrentThread.Abort(n); 28 } 29 Thread.Sleep(300); 30 Console.WriteLine("The number is:" + n.ToString()); 31 } 32 } 33 catch (ThreadAbortException ex) 34 { 35 //Output the value of n when the thread is terminated
36 if (ex.ExceptionState != null) 37 Console.WriteLine(string.Format("Thread abort when the number is: {0}!", 38 ex.ExceptionState.ToString())); 39 40 //Cancel the termination and continue to execute thread
41 Thread.ResetAbort(); 42 Console.WriteLine("Thread ResetAbort!"); 43 } 44 45 //The thread ends
46 Console.WriteLine("Thread Close!"); 47 }

The running result is as follows

Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=326146400&siteId=291194637