C # thread synchronization -- lock, monitor, mutex (excerpt)

Source: Internet
Author: User

Thread: A thread is an independent execution unit of a process. Each process has a main thread, except that the main thread can contain other threads.

The significance of multithreading: multithreading helps improve the overall responsiveness of the program and improve the CPU efficiency.

Multi-threaded application domains are quite unstable because multiple threads can run shared functional modules at the same time. To protect the application's resources from being destroyed, three locking mechanisms are provided for the multi-threaded program: The monitor class, the lock keyword, And the mutex class.

1. Lock

The lock function is to ensure that the entered thread does not interrupt the current thread, but waits until the end of the current thread for execution to continue.

Application:

Private object thislock = new object ();

Lock (thislock ){

// Lock the code block

}

Note:Avoid lockingPublicType. Otherwise, the instance is out of the control range of the Code.

Common StructureLock (this),Lock (typeof (mytype ))AndLock ("mylock ")

Violation of this rule: if the instance can be accessed by the publicLock (this)Problem.

IfMytypePublic access is allowed.Lock (typeof (mytype ))Problem.

Because any other code using the same string in the process will share the same lockLock ("mylock ")Problem.

The best practice is to definePrivateObject To lock, orPrivate StaticObject variables to protect the data shared by all instances.

The following is an example of the lock application:

In the following example, five threads are created, and the task completed by the thread is: Output thread code, with a delay of 1 second, and then output the time at that time.

Example:

 

Code

Using system;
Using system. Collections. Generic;
Using system. LINQ;
Using system. text;
Using system. Threading;

Namespace consoleapplication5 {
Class program {
Static void main (string [] ARGs ){
Console. writeline ("program start time:" + datetime. Now. tostring ());
Example EX = new example ();
Thread [] threads = new thread [5];
For (INT I = 0; I <5; I ++)
{
Threads [I] = new thread (New threadstart (ex. Output ));
Threads [I]. Name = string. Format ("worker thread # {0}", I );
}
Foreach (thread t in threads ){
T. Start ();
}
Console. writeline ("the last code of the main thread! "+ Datetime. Now. tostring ());
}
}
Class Example {
Private Static object thislock = new object ();
Public void output ()
{
Lock (thislock ){
Console. writeline ("-> {0}", thread. currentthread. Name );
Thread. Sleep (1000 );
Console. writeline (datetime. Now );
}
}

}
}

The experiment results are as follows:

Figure 1: Add lock

Figure 2: No lock

From the experiment results, we can see that after the lock is added, the program can only execute one thread at a time. Only when the current thread is finished will the next thread be executed.

No lock is added, program execution is chaotic, and blocking is easy.

2. Monitor

Lock is an encapsulation of enter and exit of monitor. Therefore, the combination of enter () and exit () Methods of the monitor class can be replaced by the lock keyword..

In addition to the lock function, the monitor class also has the following functions:

Tryenter () solves the problem of long-term crashes. If a concurrency occurs frequently and lasts for a long time, tryenter can effectively prevent deadlocks or long waits.

Wait () releases the lock on the object to allow other threads to lock and access the object. When other threads access an object, the calling thread will wait. The pulse signal is used to notify the waiting thread of changes to the object state.

Pulse (), pulseall () sends signals to one or more waiting threads. This signal indicates that the status of the waiting thread lock object has changed, and the lock owner is ready to release the lock. Wait for the thread to be placed in the ready queue of the object so that it can finally receive the object lock. Once the thread has a lock, it can check the new State of the object to see if it has reached the desired state.

Note: The pulse, pulseall, and wait methods must be called from the synchronized code block.

3. mutex (mutex)

Mutex features exclusive access to resources across application domain boundaries, that is, it can be used to synchronize threads in different processes. This feature sacrifices more system resources.

Mutex and event object eventwaithandler belong to the kernel object. When using the kernel object for thread synchronization, the thread must be switched between the user mode and the kernel mode, so the efficiency is generally low, however, kernel objects such as mutex objects and event objects can be synchronized between various threads in multiple processes.

Mutex is similar to a baton. The thread that obtains the baton can start running. Of course, the baton only belongs to one thread (thread affinity) at a time. If this thread does not release the baton (mutex. releasemutex), so all other threads that need to run the baton can only wait to watch the fun.

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.