Multithreading: C # thread synchronization lock, monitor, mutex, synchronization event and wait handle (medium)

Source: Internet
Author: User
Tags net thread

Previous: multithreading: C # thread synchronization lock, monitor, mutex, synchronization event and wait handle (on)

This article continues to introduce the waithandler class and its sub-classes mutex, manualresetevent, and autoresetevent usage .. Net Thread Synchronization Methods are dazzling. How can this problem be understood?In fact, when we look at thread synchronization in the. NET environment, we simply execute two types of operations: mutex/lock, to ensure the critical sectionCodeThe "atomicity" of the operation; the other is the traffic light operation, which aims to ensure that multiple threads are executed in a certain order. For example, the producer thread must be executed before the consumer thread.. The thread synchronization class in net is nothing more than encapsulation of the two methods. In the final analysis, the goal can be attributed to the mutual exclusion, lock, or traffic signal, but they are not applicable in some cases. The following describes the waithandler and its sub-classes based on the class hierarchy.

1. waithandler

Waithandle is the ancestor of mutex, semaphore, eventwaithandler, autoresetevent, and manualresetevent. It encapsulates the kernel objects of Win32 synchronization handles, that is, the managed versions of these kernel objects.

The thread can block a single Wait handle by calling the waithandler instance method waitone. In addition, the waithandler class reloads the static method to wait until all specified wait handles have collected the signal waitall, or wait for a specified wait handle to collect the signal waitany. These methods provide the opportunity to discard the wait timeout interval, exit the synchronization context before entering the wait, and allow other threads to use the synchronization context. Waithandler is in C #Abstract class, Cannot be instantiated.

2. eventwaithandler vs. manualresetevent vs. autoresetevent (synchronization event)

Let's take a look at the implementation of manualresetevent and autoresetevent In the. NET Framework:

Implementation of manualresetevent and autoresetevent
// Implementation of manualresetevent class in. NET Framework
[Comvisible ( True ), Hostprotection (securityaction. linkdemand, synchronization =   True , Externalthreading =   True )]
Public   Sealed   Class Manualresetevent: eventwaithandle
{
// Methods
Public Manualresetevent ( Bool Initialstate ): Base (Initialstate, eventresetmode. manualreset)
{
}
}

// Implementation of the autoresetevent class in. NET Framework
[Comvisible ( True ), Hostprotection (securityaction. linkdemand, synchronization =   True , Externalthreading =   True )]
Public   Sealed   Class Autoresetevent: eventwaithandle
{
// Methods
Public Autoresetevent ( Bool Initialstate)
: Base (Initialstate, eventresetmode. autoreset)
{
}
}

Originally, both manualresetevent and autoresetevent are inherited from eventwaithandler. The only difference between them is that the eventresetmode parameter of the eventwaithandler class is different. In this way, we only need to clarify that the eventresetmode parameter value is different, the eventwaithandler class controls the synchronization behavior of threads, so the two subclasses are clear. For ease of description, we will not introduce the two modes of the parent class, but will directly introduce the child classes.

what manualresetevent and autoresetevent have in common:
1) the set method sets the event status to terminated, one or more waiting threads are allowed to continue. The reset method sets the event status to a non-terminating State, leading to thread blocking. waitone blocks the current thread until the waithandler of the current thread receives the event signal.
2) the initial state can be determined by the constructor parameter value. If it is true, the event is terminated so that the thread is not blocked. If it is false, the thread is blocked.
3) if a thread calls the waitone method, when the event state is terminated, the thread will receive a signal and continue to execute.

Differences between manualresetevent and autoresetevent:
1) autoresetevent. waitone () allows only one thread to enter each time. When a thread receives a signal, autoresetevent automatically sets the signal to "not sent". Other threads that call waitone only need to wait, that is to say, autoresetevent only wakes up one thread at a time;
2) manualresetevent can wake up multiple threads, because when a thread calls manualresetevent. after the Set () method, other threads that call waitone can continue to execute the signal, while manualresetevent does not automatically set the signal to not send.
3) that is to say, unless the manualresetevent. Reset () method is manually called, manualresetevent will remain in a signal state, and manualresetevent will be able to wake up multiple threads to continue execution at the same time.

Example scenario: Zhang San and Li Si, two good friends, went to a restaurant to have dinner. They ordered a piece of kung pao chicken Ding, which took some time to complete. Zhang San and Li Si did not want to be stupid. They all played mobile games with their own aspirations, the waiter will definitely call us if I want to finish the work. After the waiter served the food, Michael Jacob began to enjoy the delicious food. after eating the food, they asked the waiter to pay for the food. We can abstract three threads from this scenario: three threads, three threads, four threads, and the waiter threads. They need to be synchronized: serving as a waiter-> Michael Zhang and Mr. Li start to enjoy kung pao chicken-> after dinner, ask the waiter to pay the bill. What is the use of this synchronization? Manualresetevent or autoresetevent? The above analysis shows that we should use manualresetevent for synchronization. below isProgramCode:

The story of Michael Jacob's dinner
Public   Class Eventwaittest
{
Private   String Name; // CUSTOMER NAME
// Private Static autoresetevent eventwait = new autoresetevent (false );
Private   Static Manualresetevent eventwait =   New Manualresetevent ( False );
Private   Static Manualresetevent eventover =   New Manualresetevent ( False );

PublicEventwaittest (StringName)
{
This. Name=Name;
}

Public   Static   Void Product ()
{
Console. writeline ( " Waiter: the cook is cooking. Please wait. " );
Thread. Sleep ( 2000 );
Console. writeline ( " Waiter: kung pao chicken " );
Eventwait. Set ();
While ( True )
{
If (Eventover. waitone ( 1000 , False ))
{
Console. writeline ( " Waiter: pay for the order. " );
Eventover. Reset ();
}
}
}

Public   Void Consume ()
{
While ( True )
{
If (Eventwait. waitone ( 1000 , False ))
{
Console. writeline ( This . Name +   " : Start eating kung pao chicken " );
Thread. Sleep ( 2000 );
Console. writeline ( This . Name +   " : The chicken is eaten up. " );
Eventwait. Reset ();
Eventover. Set ();
Break ;
}
Else
{
Console. writeline ( This . Name +   " : Waiting for the food to be boring. " );
}
}
}
}

Public   Class App
{
Public   Static   Void Main ( String [] ARGs)
{
Eventwaittest zhangsan =   New Eventwaittest ( " Zhang San " );
Eventwaittest Lisi =   New Eventwaittest ( " Li Si " );

Thread T1 =   New Thread ( New Threadstart (zhangsan. Consume ));
Thread T2 =   New Thread ( New Threadstart (Lisi. Consume ));
Thread T3 =   New Thread ( New Threadstart (eventwaittest. Product ));

T1.start ();
T2.start ();
T3.start ();

Console. Read ();
}
}


Check the running result after compilation. The console output is as follows:
Waiter: the cook is cooking. Please wait...
Michael Zhang: waiting for the food to be served.
Li Si: waiting for the food to be boring.
Michael Zhang: waiting for the food to be served.
Li Si: waiting for the food to be boring.
Waiter: kung pao chicken
Michael Zhang: start eating kung pao chicken
Li Si: start eating kung pao chicken
Michael Zhang: I have eaten the chicken.
Li Si: the chicken is eaten up.
Waiter: pay for the order.

What if I use autoresetevent for synchronization? What will happen? I'm afraid Zhang and Li are about to fight. One of them is enjoying the delicious kung pao chicken, and the other is still playing games when it comes to paying the bills. If you are interested, you can remove the comments of the line of code and comment out the following line of code. Run the program to see what the results will look like.

3. mutex (mutex)

Mutex and eventwaithandler share the same parent class waithandler, and their synchronous function usage is similar. Mutex features exclusive access to resources across application domain boundaries.Used to synchronize threads in different processesOf course, this is at the expense of more system resources.

One application of cross-process synchronization is to restrict the opening of two identical programs in the same brain at the same time. For specific implementation, refer to "use mutex or process to restrict users to open two programs simultaneously on one computer".

References: autoresetevent and manualresetevent,. Net thread troubleshooting

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.