Mutex クラス

定義

同期プリミティブは、プロセス間の同期にも使用できます。

public ref class Mutex sealed : System::Threading::WaitHandle
public sealed class Mutex : System.Threading.WaitHandle
[System.Runtime.InteropServices.ComVisible(true)]
public sealed class Mutex : System.Threading.WaitHandle
type Mutex = class
    inherit WaitHandle
[<System.Runtime.InteropServices.ComVisible(true)>]
type Mutex = class
    inherit WaitHandle
Public NotInheritable Class Mutex
Inherits WaitHandle
継承
継承
属性

この例では、ローカル オブジェクトを Mutex 使用して保護されたリソースへのアクセスを同期する方法を示します。 呼び出し元の各スレッドはミューテックスの所有権を取得するまでブロックされます。ため、 メソッドを呼び出してミューテックスの所有権 ReleaseMutex を解放する必要があります。

using System;
using System.Threading;

class Example
{
    // Create a new Mutex. The creating thread does not own the mutex.
    private static Mutex mut = new Mutex();
    private const int numIterations = 1;
    private const int numThreads = 3;

    static void Main()
    {
        // Create the threads that will use the protected resource.
        for(int i = 0; i < numThreads; i++)
        {
            Thread newThread = new Thread(new ThreadStart(ThreadProc));
            newThread.Name = String.Format("Thread{0}", i + 1);
            newThread.Start();
        }

        // The main thread exits, but the application continues to
        // run until all foreground threads have exited.
    }

    private static void ThreadProc()
    {
        for(int i = 0; i < numIterations; i++)
        {
            UseResource();
        }
    }

    // This method represents a resource that must be synchronized
    // so that only one thread at a time can enter.
    private static void UseResource()
    {
        // Wait until it is safe to enter.
        Console.WriteLine("{0} is requesting the mutex", 
                          Thread.CurrentThread.Name);
        mut.WaitOne();

        Console.WriteLine("{0} has entered the protected area", 
                          Thread.CurrentThread.Name);

        // Place code to access non-reentrant resources here.

        // Simulate some work.
        Thread.Sleep(500);

        Console.WriteLine("{0} is leaving the protected area", 
            Thread.CurrentThread.Name);

        // Release the Mutex.
        mut.ReleaseMutex();
        Console.WriteLine("{0} has released the mutex", 
            Thread.CurrentThread.Name);
    }
}
// The example displays output like the following:
//       Thread1 is requesting the mutex
//       Thread2 is requesting the mutex
//       Thread1 has entered the protected area
//       Thread3 is requesting the mutex
//       Thread1 is leaving the protected area
//       Thread1 has released the mutex
//       Thread3 has entered the protected area
//       Thread3 is leaving the protected area
//       Thread3 has released the mutex
//       Thread2 has entered the protected area
//       Thread2 is leaving the protected area
//       Thread2 has released the mutex
Imports System.Threading

Module Example
   ' Create a new Mutex. The creating thread does not own the mutex.
   Private mut As New Mutex()
   Private Const numIterations As Integer = 1
   Private Const numThreads As Integer = 3
   
   Public Sub Main()
        ' Create the threads that will use the protected resource.
        For i As Integer = 0 To numThreads - 1
            Dim newThread As New Thread(AddressOf ThreadProc)
            newThread.Name = String.Format("Thread{0}", i + 1)
            newThread.Start()
        Next

        ' The main thread exits, but the application continues to
        ' run until all foreground threads have exited.
    End Sub

    Private Sub ThreadProc()
        For i As Integer = 0 To numIterations - 1
            UseResource()
        Next
    End Sub

    ' This method represents a resource that must be synchronized
    ' so that only one thread at a time can enter.
    Private Sub UseResource()
        ' Wait until it is safe to enter.
        Console.WriteLine("{0} is requesting the mutex", 
                          Thread.CurrentThread.Name)
        mut.WaitOne()

        Console.WriteLine("{0} has entered the protected area", 
                          Thread.CurrentThread.Name)

        ' Place code to access non-reentrant resources here.

        ' Simulate some work.
        Thread.Sleep(500)

        Console.WriteLine("{0} is leaving the protected area", 
            Thread.CurrentThread.Name)

        ' Release the Mutex.
        mut.ReleaseMutex()
        Console.WriteLine("{0} has released the mutex", 
            Thread.CurrentThread.Name)
   End Sub
End Module
' The example displays output like the following:
'       Thread1 is requesting the mutex
'       Thread2 is requesting the mutex
'       Thread1 has entered the protected area
'       Thread3 is requesting the mutex
'       Thread1 is leaving the protected area
'       Thread1 has released the mutex
'       Thread3 has entered the protected area
'       Thread3 is leaving the protected area
'       Thread3 has released the mutex
'       Thread2 has entered the protected area
'       Thread2 is leaving the protected area
'       Thread2 has released the mutex

次の例では、各スレッドは メソッドを呼 WaitOne(Int32) び出してミューテックスを取得します。 タイム アウト間隔が経過すると、 メソッドは を返し、スレッドはミューテックスを取得したり、ミューテックスが保護するリソースにアクセス false したりします。 メソッド ReleaseMutex は、ミューテックスを取得するスレッドによってのみ呼び出されます。

using System;
using System.Threading;

class Example
{
    // Create a new Mutex. The creating thread does not own the mutex.
    private static Mutex mut = new Mutex();
    private const int numIterations = 1;
    private const int numThreads = 3;

    static void Main()
    {
        Example ex = new Example();
        ex.StartThreads();
    }

     private void StartThreads()
     {
        // Create the threads that will use the protected resource.
        for(int i = 0; i < numThreads; i++)
        {
            Thread newThread = new Thread(new ThreadStart(ThreadProc));
            newThread.Name = String.Format("Thread{0}", i + 1);
            newThread.Start();
        }

        // The main thread returns to Main and exits, but the application continues to
        // run until all foreground threads have exited.
    }

    private static void ThreadProc()
    {
        for(int i = 0; i < numIterations; i++)
        {
            UseResource();
        }
    }

    // This method represents a resource that must be synchronized
    // so that only one thread at a time can enter.
    private static void UseResource()
    {
        // Wait until it is safe to enter, and do not enter if the request times out.
        Console.WriteLine("{0} is requesting the mutex", Thread.CurrentThread.Name);
        if (mut.WaitOne(1000)) {
           Console.WriteLine("{0} has entered the protected area", 
               Thread.CurrentThread.Name);
   
           // Place code to access non-reentrant resources here.
   
           // Simulate some work.
           Thread.Sleep(5000);
   
           Console.WriteLine("{0} is leaving the protected area", 
               Thread.CurrentThread.Name);
   
           // Release the Mutex.
              mut.ReleaseMutex();
           Console.WriteLine("{0} has released the mutex", 
                             Thread.CurrentThread.Name);
        }
        else {
           Console.WriteLine("{0} will not acquire the mutex", 
                             Thread.CurrentThread.Name);
        }
    }

    ~Example()
    {
       mut.Dispose();
    }
}
// The example displays output like the following:
//       Thread1 is requesting the mutex
//       Thread1 has entered the protected area
//       Thread2 is requesting the mutex
//       Thread3 is requesting the mutex
//       Thread2 will not acquire the mutex
//       Thread3 will not acquire the mutex
//       Thread1 is leaving the protected area
//       Thread1 has released the mutex
Imports System.Threading

Class Example
   ' Create a new Mutex. The creating thread does not own the mutex.
   Private mut As New Mutex()
   Private Const numIterations As Integer = 1
   Private Const numThreads As Integer = 3

   Public Shared Sub Main()
      Dim ex As New Example()
      ex.StartThreads()
   End Sub
   
   Private Sub StartThreads()
        ' Create the threads that will use the protected resource.
        For i As Integer = 0 To numThreads - 1
            Dim newThread As New Thread(AddressOf ThreadProc)
            newThread.Name = String.Format("Thread{0}", i + 1)
            newThread.Start()
        Next

        ' The main thread returns to Main and exits, but the application continues to
        ' run until all foreground threads have exited.
   End Sub

   Private Sub ThreadProc()
        For i As Integer = 0 To numIterations - 1
            UseResource()
        Next
   End Sub

   ' This method represents a resource that must be synchronized
   ' so that only one thread at a time can enter.
   Private Sub UseResource()
        ' Wait until it is safe to enter.
        Console.WriteLine("{0} is requesting the mutex", 
                          Thread.CurrentThread.Name)
        If mut.WaitOne(1000) Then
           Console.WriteLine("{0} has entered the protected area", 
               Thread.CurrentThread.Name)
   
           ' Place code to access non-reentrant resources here.
   
           ' Simulate some work.
           Thread.Sleep(5000)
   
           Console.WriteLine("{0} is leaving the protected area", 
               Thread.CurrentThread.Name)
   
           ' Release the Mutex.
           mut.ReleaseMutex()
           Console.WriteLine("{0} has released the mutex", 
                             Thread.CurrentThread.Name)
        Else
           Console.WriteLine("{0} will not acquire the mutex", 
                             Thread.CurrentThread.Name)
        End If
   End Sub
   
   Protected Overrides Sub Finalize()
      mut.Dispose()
   End Sub
End Class
' The example displays output like the following:
'       Thread1 is requesting the mutex
'       Thread1 has entered the protected area
'       Thread2 is requesting the mutex
'       Thread3 is requesting the mutex
'       Thread2 will not acquire the mutex
'       Thread3 will not acquire the mutex
'       Thread1 is leaving the protected area
'       Thread1 has released the mutex

注釈

2 つ以上のスレッドが共有リソースに同時にアクセスする必要がある場合は、一度に 1 つのスレッドだけがリソースを使用する同期メカニズムが必要です。 Mutex は、共有リソースへの排他的アクセスを 1 つのスレッドにのみ許可する同期プリミティブです。 スレッドがミューテックスを取得した場合、そのミューテックスを取得する 2 番目のスレッドは、最初のスレッドがミューテックスを解放するまで中断されます。

重要

この型は IDisposable インターフェイスを実装します。 型の使用が完了したら、直接的または間接的に型を破棄する必要があります。 直接的に型を破棄するには、try/catch ブロック内で Dispose メソッドを呼び出します。 間接的に型を破棄するには、using (C# の場合) または Using (Visual Basic 言語) などの言語構成要素を使用します。 詳細については、IDisposable インターフェイスに関するトピック内の「IDisposable を実装するオブジェクトの使用」セクションを参照してください。

メソッドを使用 WaitHandle.WaitOne してミューテックスの所有権を要求できます。 呼び出し元のスレッドは、次のいずれかの処理が行われるまでブロックされます。

  • ミューテックスは、所有されていないかどうかを示すために通知されます。 この場合、 メソッドは を返し、呼び出し元のスレッドはミューテックスの所有権を想定し、ミューテックスによって保護されているリソース WaitOne true にアクセスします。 リソースへのアクセスが完了したら、スレッドは メソッドを呼び出してミューテックスの所有権 ReleaseMutex を解放する必要があります。 「例」セクションの最初の例は、このパターンを示しています。

  • パラメーターまたは パラメーターを持つメソッドの呼び出しで指定されたタイム WaitOne millisecondsTimeout アウト timeout 間隔が経過しました。 この場合、メソッドは を返し、呼び出し元のスレッドはミューテックスの所有権の取得をそれ以上 WaitOne false 試みない状態です。 この場合は、ミューテックスによって保護されているリソースへのアクセスが呼び出し元のスレッドに対して拒否されるコードを構造化する必要があります。 スレッドはミューテックスの所有権を取得したことがないので、 メソッドを呼び出す ReleaseMutex 必要があります。 「例」セクションの 2 番目の例は、このパターンを示しています。

クラスはスレッド ID を強制します。そのため、ミューテックスは、それを取得したスレッド Mutex でのみ解放できます。 これに対し、 クラス Semaphore はスレッド ID を強制しない。 ミューテックスは、アプリケーション ドメインの境界を越えて渡される場合があります。

ミューテックスを所有するスレッドは、実行をブロックすることなく、 の繰り返し呼び出しで WaitOne 同じミューテックスを要求できます。 ただし、ミューテックスの所有権を解放するには、スレッドがメソッドを同じ回数呼び出 ReleaseMutex す必要があります。

クラスは から継承されます。また、静的メソッドと メソッドを呼び出して、保護されたリソースへのアクセス Mutex WaitHandle WaitHandle.WaitAll WaitHandle.WaitAny を同期できます。

ミューテックスの所有中にスレッドが終了した場合、ミューテックスは破棄されたと言います。 ミューテックスの状態が signaled に設定され、次の待機中のスレッドが所有権を取得します。 バージョン 2.0 の .NET Framework、破棄されたミューテックスを取得する次のスレッドで AbandonedMutexException がスローされます。 バージョン 2.0 より前のバージョン.NET Framework、例外はスローはありませんでした。

注意事項

破棄されたミューテックスは、多くの場合、コード内の重大なエラーを示します。 ミューテックスを解放せずにスレッドが終了すると、ミューテックスによって保護されているデータ構造が一貫した状態ではない可能性があります。 ミューテックスの所有権を要求する次のスレッドは、データ構造の整合性を確認できる場合、この例外を処理して続行できます。

システム全体でミューテックスが有効な場合にミューテックスが破棄されたときは、アプリケーションが強制終了されたことを示している可能性があります (たとえば、Windows タスク マネージャを使用した終了)。

ミューテックスには、名前のないローカル ミューテックスと名前付きシステム ミューテックスの 2 種類があります。 ローカル ミューテックスは、現在のプロセス内にのみ存在します。 ミューテックスを表す オブジェクトへの参照を持つプロセス内の任意のスレッド Mutex で使用できます。 名前のない各オブジェクト Mutex は、個別のローカル ミューテックスを表します。

名前付きシステム ミューテックスはオペレーティング システム全体で表示され、プロセスのアクティビティを同期するために使用できます。 名前を受け Mutex 取るコンストラクターを使用して、名前付きシステム ミューテックスを表す オブジェクトを作成できます。 オペレーティング システム オブジェクトは、同時に作成するか、オブジェクトを作成する前に存在 Mutex することができます。 同じ名前付きシステム ミューテックスを表す複数の Mutex オブジェクトを作成できます。また、OpenExisting メソッドを使用して、既存の名前付きシステム ミューテックスを開くことができます。

注意

ターミナル サービスを実行しているサーバーでは、名前付きシステム ミューテックスに 2 つのレベルの可視性を設定できます。 その名前がプレフィックス "Global " で始まる場合、ミューテックスは、すべてのターミナル \ サーバー セッションで表示されます。 名前が "Local" というプレフィックスで始まる場合、ミューテックスは、それが作成されたターミナル サーバー \ セッションでのみ表示されます。 その場合、同じ名前の個別のミューテックスが、サーバー上の他の各ターミナル サーバー セッションに存在する可能性があります。 名前付きミューテックスを作成するときにプレフィックスを指定しない場合は、プレフィックス "Local" を受け取る \ 。 ターミナル サーバー セッション内では、名前がプレフィックスによってのみ異なる 2 つのミューテックスは個別のミューテックスであり、両方ともターミナル サーバー セッション内のすべてのプロセスに表示されます。 つまり、プレフィックス名 "Global" と "Local" は、プロセスに対する相対ではなく、ターミナル サーバー セッションに対するミューテックス名のスコープ \ \ を記述します。

円記号 (\) は、ミューテックス名の予約文字です。 ターミナル サーバー セッションのミューテックス使用に関する注記に指定されていない限り、ミューテックス名に円記号 (\) を使用しないでください。 使用した場合、ミューテックスの名前が既存のファイルを表すとしても、DirectoryNotFoundException がスローされることがあります。

コンストラクター

Mutex()

Mutex クラスの新しいインスタンスを、既定のプロパティを使用して初期化します。

Mutex(Boolean)

呼び出し元のスレッドにミューテックスの初期所有権があるかどうかを示すブール値を使用して、Mutex クラスの新しいインスタンスを初期化します。

Mutex(Boolean, String)

呼び出し元のスレッドにミューテックスの初期所有権があるかどうかを示すブール値と、ミューテックスの名前を表す文字列を使用して、Mutex クラスの新しいインスタンスを初期化します。

Mutex(Boolean, String, Boolean)

呼び出し元のスレッドにミューテックスの初期所有権があるかどうかを示すブール値、ミューテックスの名前を表す文字列、およびメソッドから戻るときにミューテックスの初期所有権が呼び出し元のスレッドに付与されたかどうかを示すブール値を指定して、Mutex クラスの新しいインスタンスを初期化します。

Mutex(Boolean, String, Boolean, MutexSecurity)

呼び出し元のスレッドにミューテックスの初期所有権があるかどうかを示すブール値、ミューテックスの名前を表す文字列、メソッドが戻るときにミューテックスの初期所有権が呼び出し元のスレッドに付与されたかどうかを示すブール値変数、および名前付きミューテックスに適用するアクセス制御セキュリティを指定して、Mutex クラスの新しいインスタンスを初期化します。

フィールド

WaitTimeout

待機ハンドルがシグナル状態になる前に WaitAny(WaitHandle[], Int32, Boolean) 操作がタイムアウトになったことを示します。 このフィールドは定数です。

(継承元 WaitHandle)

プロパティ

Handle
互換性のために残されています。
互換性のために残されています。

ネイティブ オペレーティング システム ハンドルを取得または設定します。

(継承元 WaitHandle)
SafeWaitHandle

ネイティブ オペレーティング システム ハンドルを取得または設定します。

(継承元 WaitHandle)

メソッド

Close()

現在の WaitHandle によって保持されているすべてのリソースを解放します。

(継承元 WaitHandle)
CreateObjRef(Type)

リモート オブジェクトとの通信に使用するプロキシの生成に必要な情報をすべて格納しているオブジェクトを作成します。

(継承元 MarshalByRefObject)
Dispose()

WaitHandle クラスの現在のインスタンスによって使用されているすべてのリソースを解放します。

(継承元 WaitHandle)
Dispose(Boolean)

派生クラスでオーバーライドされると、WaitHandle によって使用されているアンマネージド リソースを解放し、オプションでマネージド リソースも解放します。

(継承元 WaitHandle)
Equals(Object)

指定されたオブジェクトが現在のオブジェクトと等しいかどうかを判断します。

(継承元 Object)
GetAccessControl()

名前付きミューテックスのアクセス制御セキュリティを表す MutexSecurity オブジェクトを取得します。

GetHashCode()

既定のハッシュ関数として機能します。

(継承元 Object)
GetLifetimeService()
互換性のために残されています。

対象のインスタンスの有効期間ポリシーを制御する、現在の有効期間サービス オブジェクトを取得します。

(継承元 MarshalByRefObject)
GetType()

現在のインスタンスの Type を取得します。

(継承元 Object)
InitializeLifetimeService()
互換性のために残されています。

このインスタンスの有効期間ポリシーを制御する有効期間サービス オブジェクトを取得します。

(継承元 MarshalByRefObject)
MemberwiseClone()

現在の Object の簡易コピーを作成します。

(継承元 Object)
MemberwiseClone(Boolean)

現在の MarshalByRefObject オブジェクトの簡易コピーを作成します。

(継承元 MarshalByRefObject)
OpenExisting(String)

既に存在する場合は、指定した名前付きミューテックスを開きます。

OpenExisting(String, MutexRights)

既に存在する場合は、必要なセキュリティ アクセスで指定した名前付きミューテックスを開きます。

ReleaseMutex()

Mutex を一度解放します。

SetAccessControl(MutexSecurity)

名前付きシステム ミューテックスのアクセス制御セキュリティを設定します。

ToString()

現在のオブジェクトを表す文字列を返します。

(継承元 Object)
TryOpenExisting(String, Mutex)

既に存在する場合は、指定した名前付きミューテックスを開き操作が成功したかどうかを示す値を返します。

TryOpenExisting(String, MutexRights, Mutex)

既に存在する場合は、必要なセキュリティ アクセスを使用して指定した名前付きミューテックスを開き、操作が成功したかどうかを示す値を返します。

WaitOne()

現在の WaitHandle がシグナルを受け取るまで、現在のスレッドをブロックします。

(継承元 WaitHandle)
WaitOne(Int32)

32 ビット符号付き整数を使用して時間間隔をミリ秒単位で指定し、現在の WaitHandle がシグナルを受信するまで、現在のスレッドをブロックします。

(継承元 WaitHandle)
WaitOne(Int32, Boolean)

現在の WaitHandle がシグナルを受信するまで現在のスレッドをブロックします。時間間隔を指定するために 32 ビット符号付き整数を使用し、待機の前でも同期ドメインを終了するかどうかを指定します。

(継承元 WaitHandle)
WaitOne(TimeSpan)

TimeSpan を使用して時間間隔を指定し、現在のインスタンスがシグナルを受信するまで現在のスレッドをブロックします。

(継承元 WaitHandle)
WaitOne(TimeSpan, Boolean)

現在のインスタンスがシグナルを受信するまで現在のスレッドをブロックします。TimeSpan を使用して時間間隔を指定し、待機の前でも同期ドメインを終了するかどうかを指定します。

(継承元 WaitHandle)

明示的なインターフェイスの実装

IDisposable.Dispose()

この API は製品インフラストラクチャをサポートします。コードから直接使用するものではありません。

WaitHandle によって使用されているすべてのリソースを解放します。

(継承元 WaitHandle)

拡張メソッド

GetAccessControl(Mutex)

指定した mutex のセキュリティ記述子を返します。

SetAccessControl(Mutex, MutexSecurity)

指定したミューテックスのセキュリティ記述子を設定します。

GetSafeWaitHandle(WaitHandle)

ネイティブ オペレーティング システムの待機ハンドルのためのセーフ ハンドルを取得します。

SetSafeWaitHandle(WaitHandle, SafeWaitHandle)

ネイティブ オペレーティング システムの待機ハンドルのためのセーフ ハンドルを設定します。

適用対象

スレッド セーフ

この型はスレッド セーフです。

こちらもご覧ください