Mutex:互斥体对象。
互斥的范围:多进程范围内的互斥,也可以用于同进程多线程的同步,如果应用场景是同一进程类的互斥,Mutex就没有使用的必要了,使用Lock或Monitor应该是比较好的选择。因为Mutex的获取与生成比Lock或Monitor慢了不至一个数量级。
本地Mutex:如果在构造Mutex对象时不传递命名参数,则会构造本地Mutex,本地Mutex用于同进程内的多线程同步.
系统Mutex:构造Mutex必须传递命名,系统Mutex用于多进程中的同步。
代码如下:
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading; namespace ThreadPrint { /// <summary> /// Mutex:互斥范围:跨进程。 /// 测试1:先运行ThreadPrint 产生线程1, /// 然后再次运行ThreadPrint产生线程2,线程1调用ReleaseMutex() 释放后,线程2会立即执行 /// 测试2:先运行ThreadPrint 产生进程1, /// 然后再次运行ThreadPrint,产生进程2,然后关闭进程1,进程2就会引发AbandonedMutexException异常 /// /// </summary> class MutexTest { public static void Test() { //命名的互斥体在终端上唯一标识 using (var mutex = new Mutex(false, "Hbb0b0")) { try { //WaitOne 判断是否有其它进程占有互斥体。 //如果Mutex被其它进程占有,那么当前进程等待30秒,如果在30秒之中其它进程终止前没有释放Mutex, //那么当前线程会立即收到AbandonedMutexException 异常。 //mutex.WaitOne(TimeSpan.FromSeconds(30), false ) //如果Mutex被其它进程占有,那么当前进程等待30秒,如果在30秒之中其它进程释放了Mutex, //那么当前线程会立即解除阻止而继续执行。 if (!mutex.WaitOne(TimeSpan.FromSeconds(30))) { Console.WriteLine("Another app instance is running. Bye!"); return; } } //其他进程释放了互斥体 catch(AbandonedMutexException e) { Console.WriteLine(e.Message); } RunProgram(); Thread.Sleep(10000); mutex.ReleaseMutex(); Console.WriteLine("mutex.ReleaseMutex()"); } } static void RunProgram() { Console.WriteLine("Running. Press Enter to exit"); } } }