ManualResetEvent 类  
定义
重要
一些信息与预发行产品相关,相应产品在发行之前可能会进行重大修改。 对于此处提供的信息,Microsoft 不作任何明示或暗示的担保。
表示必须手动重置信号的线程同步事件。 无法继承此类。
public ref class ManualResetEvent sealed : System::Threading::EventWaitHandlepublic ref class ManualResetEvent sealed : System::Threading::WaitHandlepublic sealed class ManualResetEvent : System.Threading.EventWaitHandlepublic sealed class ManualResetEvent : System.Threading.WaitHandle[System.Runtime.InteropServices.ComVisible(true)]
public sealed class ManualResetEvent : System.Threading.EventWaitHandletype ManualResetEvent = class
    inherit EventWaitHandletype ManualResetEvent = class
    inherit WaitHandle[<System.Runtime.InteropServices.ComVisible(true)>]
type ManualResetEvent = class
    inherit EventWaitHandlePublic NotInheritable Class ManualResetEvent
Inherits EventWaitHandlePublic NotInheritable Class ManualResetEvent
Inherits WaitHandle- 继承
- 继承
- 继承
- 属性
示例
以下示例演示如何 ManualResetEvent 工作。 该示例以处于无对齐状态的 ManualResetEvent(即 false 传递给构造函数)开头。 该示例创建三个线程,每个线程通过调用 WaitOne 方法在 ManualResetEvent 上阻止。 当用户按下 Enter 键时,该示例将调用 Set 方法,该方法释放所有三个线程。 与此形成鲜明对比的是 AutoResetEvent 类的行为,该类一次释放一个线程,在每个发布后自动重置。
再次按 Enter 键表明,ManualResetEvent 保持信号状态,直到调用其 Reset 方法:本示例再启动两个线程。 这些线程在调用 WaitOne 方法时不会阻止,而是运行到完成。
再次按 Enter 键会导致示例调用 Reset 方法并启动一个线程,这会在调用 WaitOne时阻止它。 按 Enter 键一次调用 Set 释放最后一个线程,程序结束。
using namespace System;
using namespace System::Threading;
ref class Example
{
private:
    // mre is used to block and release threads manually. It is
    // created in the unsignaled state.
    static ManualResetEvent^ mre = gcnew ManualResetEvent(false);
    static void ThreadProc()
    {
        String^ name = Thread::CurrentThread->Name;
        Console::WriteLine(name + " starts and calls mre->WaitOne()");
        mre->WaitOne();
        Console::WriteLine(name + " ends.");
    }
public:
    static void Demo()
    {
        Console::WriteLine("\nStart 3 named threads that block on a ManualResetEvent:\n");
        for(int i = 0; i <=2 ; i++)
        {
            Thread^ t = gcnew Thread(gcnew ThreadStart(ThreadProc));
            t->Name = "Thread_" + i;
            t->Start();
        }
        Thread::Sleep(500);
        Console::WriteLine("\nWhen all three threads have started, press Enter to call Set()" +
                           "\nto release all the threads.\n");
        Console::ReadLine();
        mre->Set();
        Thread::Sleep(500);
        Console::WriteLine("\nWhen a ManualResetEvent is signaled, threads that call WaitOne()" +
                           "\ndo not block. Press Enter to show this.\n");
        Console::ReadLine();
        for(int i = 3; i <= 4; i++)
        {
            Thread^ t = gcnew Thread(gcnew ThreadStart(ThreadProc));
            t->Name = "Thread_" + i;
            t->Start();
        }
        Thread::Sleep(500);
        Console::WriteLine("\nPress Enter to call Reset(), so that threads once again block" +
                           "\nwhen they call WaitOne().\n");
        Console::ReadLine();
        mre->Reset();
        // Start a thread that waits on the ManualResetEvent.
        Thread^ t5 = gcnew Thread(gcnew ThreadStart(ThreadProc));
        t5->Name = "Thread_5";
        t5->Start();
        Thread::Sleep(500);
        Console::WriteLine("\nPress Enter to call Set() and conclude the demo.");
        Console::ReadLine();
        mre->Set();
        // If you run this example in Visual Studio, uncomment the following line:
        //Console::ReadLine();
    }
};
int main()
{
   Example::Demo();
}
/* This example produces output similar to the following:
Start 3 named threads that block on a ManualResetEvent:
Thread_0 starts and calls mre->WaitOne()
Thread_1 starts and calls mre->WaitOne()
Thread_2 starts and calls mre->WaitOne()
When all three threads have started, press Enter to call Set()
to release all the threads.
Thread_2 ends.
Thread_1 ends.
Thread_0 ends.
When a ManualResetEvent is signaled, threads that call WaitOne()
do not block. Press Enter to show this.
Thread_3 starts and calls mre->WaitOne()
Thread_3 ends.
Thread_4 starts and calls mre->WaitOne()
Thread_4 ends.
Press Enter to call Reset(), so that threads once again block
when they call WaitOne().
Thread_5 starts and calls mre->WaitOne()
Press Enter to call Set() and conclude the demo.
Thread_5 ends.
 */
using System;
using System.Threading;
public class Example
{
    // mre is used to block and release threads manually. It is
    // created in the unsignaled state.
    private static ManualResetEvent mre = new ManualResetEvent(false);
    static void Main()
    {
        Console.WriteLine("\nStart 3 named threads that block on a ManualResetEvent:\n");
        for(int i = 0; i <= 2; i++)
        {
            Thread t = new Thread(ThreadProc);
            t.Name = "Thread_" + i;
            t.Start();
        }
        Thread.Sleep(500);
        Console.WriteLine("\nWhen all three threads have started, press Enter to call Set()" +
                          "\nto release all the threads.\n");
        Console.ReadLine();
        mre.Set();
        Thread.Sleep(500);
        Console.WriteLine("\nWhen a ManualResetEvent is signaled, threads that call WaitOne()" +
                          "\ndo not block. Press Enter to show this.\n");
        Console.ReadLine();
        for(int i = 3; i <= 4; i++)
        {
            Thread t = new Thread(ThreadProc);
            t.Name = "Thread_" + i;
            t.Start();
        }
        Thread.Sleep(500);
        Console.WriteLine("\nPress Enter to call Reset(), so that threads once again block" +
                          "\nwhen they call WaitOne().\n");
        Console.ReadLine();
        mre.Reset();
        // Start a thread that waits on the ManualResetEvent.
        Thread t5 = new Thread(ThreadProc);
        t5.Name = "Thread_5";
        t5.Start();
        Thread.Sleep(500);
        Console.WriteLine("\nPress Enter to call Set() and conclude the demo.");
        Console.ReadLine();
        mre.Set();
        // If you run this example in Visual Studio, uncomment the following line:
        //Console.ReadLine();
    }
    private static void ThreadProc()
    {
        string name = Thread.CurrentThread.Name;
        Console.WriteLine(name + " starts and calls mre.WaitOne()");
        mre.WaitOne();
        Console.WriteLine(name + " ends.");
    }
}
/* This example produces output similar to the following:
Start 3 named threads that block on a ManualResetEvent:
Thread_0 starts and calls mre.WaitOne()
Thread_1 starts and calls mre.WaitOne()
Thread_2 starts and calls mre.WaitOne()
When all three threads have started, press Enter to call Set()
to release all the threads.
Thread_2 ends.
Thread_0 ends.
Thread_1 ends.
When a ManualResetEvent is signaled, threads that call WaitOne()
do not block. Press Enter to show this.
Thread_3 starts and calls mre.WaitOne()
Thread_3 ends.
Thread_4 starts and calls mre.WaitOne()
Thread_4 ends.
Press Enter to call Reset(), so that threads once again block
when they call WaitOne().
Thread_5 starts and calls mre.WaitOne()
Press Enter to call Set() and conclude the demo.
Thread_5 ends.
 */
Imports System.Threading
Public Class Example
    ' mre is used to block and release threads manually. It is
    ' created in the unsignaled state.
    Private Shared mre As New ManualResetEvent(False)
    <MTAThreadAttribute> _
    Shared Sub Main()
        Console.WriteLine(vbLf & _
            "Start 3 named threads that block on a ManualResetEvent:" & vbLf)
        For i As Integer = 0 To 2
            Dim t As New Thread(AddressOf ThreadProc)
            t.Name = "Thread_" & i
            t.Start()
        Next i
        Thread.Sleep(500)
        Console.WriteLine(vbLf & _
            "When all three threads have started, press Enter to call Set()" & vbLf & _
            "to release all the threads." & vbLf)
        Console.ReadLine()
        mre.Set()
        Thread.Sleep(500)
        Console.WriteLine(vbLf & _
            "When a ManualResetEvent is signaled, threads that call WaitOne()" & vbLf & _
            "do not block. Press Enter to show this." & vbLf)
        Console.ReadLine()
        For i As Integer = 3 To 4
            Dim t As New Thread(AddressOf ThreadProc)
            t.Name = "Thread_" & i
            t.Start()
        Next i
        Thread.Sleep(500)
        Console.WriteLine(vbLf & _
            "Press Enter to call Reset(), so that threads once again block" & vbLf & _
            "when they call WaitOne()." & vbLf)
        Console.ReadLine()
        mre.Reset()
        ' Start a thread that waits on the ManualResetEvent.
        Dim t5 As New Thread(AddressOf ThreadProc)
        t5.Name = "Thread_5"
        t5.Start()
        Thread.Sleep(500)
        Console.WriteLine(vbLf & "Press Enter to call Set() and conclude the demo.")
        Console.ReadLine()
        mre.Set()
        ' If you run this example in Visual Studio, uncomment the following line:
        'Console.ReadLine()
    End Sub
    Private Shared Sub ThreadProc()
        Dim name As String = Thread.CurrentThread.Name
        Console.WriteLine(name & " starts and calls mre.WaitOne()")
        mre.WaitOne()
        Console.WriteLine(name & " ends.")
    End Sub
End Class
' This example produces output similar to the following:
'
'Start 3 named threads that block on a ManualResetEvent:
'
'Thread_0 starts and calls mre.WaitOne()
'Thread_1 starts and calls mre.WaitOne()
'Thread_2 starts and calls mre.WaitOne()
'
'When all three threads have started, press Enter to call Set()
'to release all the threads.
'
'
'Thread_2 ends.
'Thread_0 ends.
'Thread_1 ends.
'
'When a ManualResetEvent is signaled, threads that call WaitOne()
'do not block. Press Enter to show this.
'
'
'Thread_3 starts and calls mre.WaitOne()
'Thread_3 ends.
'Thread_4 starts and calls mre.WaitOne()
'Thread_4 ends.
'
'Press Enter to call Reset(), so that threads once again block
'when they call WaitOne().
'
'
'Thread_5 starts and calls mre.WaitOne()
'
'Press Enter to call Set() and conclude the demo.
'
'Thread_5 ends.
注解
使用 ManualResetEvent、AutoResetEvent和 EventWaitHandle 进行线程交互(或线程信号)。 有关详细信息,请参阅 同步基元概述 一文中的 线程交互或信号 部分。
当线程开始必须在其他线程继续之前完成的活动时,它将调用 ManualResetEvent.Reset 以将 ManualResetEvent 置于非信号状态。 可以将此线程视为控制 ManualResetEvent。 调用 manualResetEvent.WaitOne 块 
发出信号后,ManualResetEvent 保持信号,直到通过调用 Reset() 方法手动重置。 也就是说,调用 WaitOne 立即返回。
可以通过将布尔值传递给构造函数来控制 ManualResetEvent 的初始状态:如果发出初始状态,则 true,否则 false。
              ManualResetEvent 还可用于 staticWaitAll 和 WaitAny 方法。
从 .NET Framework 版本 2.0 开始,ManualResetEvent 派生自 EventWaitHandle 类。 ManualResetEvent 在功能上等效于使用 EventResetMode.ManualReset创建的 EventWaitHandle。
注意
与 ManualResetEvent 类不同,EventWaitHandle 类提供对命名系统同步事件的访问权限。
从 .NET Framework 版本 4.0 开始,System.Threading.ManualResetEventSlim 类是 ManualResetEvent的轻型替代方法。
构造函数
| ManualResetEvent(Boolean) | 使用布尔值初始化 ManualResetEvent 类的新实例,该值指示是否将初始状态设置为信号。 | 
字段
| 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() | 获取一个 EventWaitHandleSecurity 对象,该对象表示由当前 EventWaitHandle 对象表示的命名系统事件的访问控制安全性。(继承自 EventWaitHandle) | 
| GetHashCode() | 用作默认哈希函数。(继承自 Object) | 
| GetLifetimeService() | 
		已过时.
	 检索控制此实例的生存期策略的当前生存期服务对象。(继承自 MarshalByRefObject) | 
| GetType() | 获取当前实例的 Type。(继承自 Object) | 
| InitializeLifetimeService() | 
		已过时.
	 获取生存期服务对象来控制此实例的生存期策略。(继承自 MarshalByRefObject) | 
| MemberwiseClone() | 创建当前 Object的浅表副本。(继承自 Object) | 
| MemberwiseClone(Boolean) | 创建当前 MarshalByRefObject 对象的浅表副本。(继承自 MarshalByRefObject) | 
| Reset() | 将事件的状态设置为非对齐状态,这会导致线程阻止。 | 
| Reset() | 将事件的状态设置为非对齐状态,导致线程被阻止。(继承自 EventWaitHandle) | 
| Set() | 将事件的状态设置为信号,这允许一个或多个等待的线程继续。 | 
| Set() | 将事件的状态设置为信号,允许一个或多个等待线程继续。(继承自 EventWaitHandle) | 
| SetAccessControl(EventWaitHandleSecurity) | 设置命名系统事件的访问控制安全性。(继承自 EventWaitHandle) | 
| ToString() | 返回一个表示当前对象的字符串。(继承自 Object) | 
| WaitOne() | 阻止当前线程,直到当前 WaitHandle 收到信号。(继承自 WaitHandle) | 
| WaitOne(Int32) | 阻止当前线程,直到当前 WaitHandle 接收信号,使用 32 位有符号整数指定时间间隔(以毫秒为单位)。(继承自 WaitHandle) | 
| WaitOne(Int32, Boolean) | 阻止当前线程,直到当前 WaitHandle 收到信号,使用 32 位有符号整数指定时间间隔,并指定是否在等待之前退出同步域。(继承自 WaitHandle) | 
| WaitOne(TimeSpan) | 阻止当前线程,直到当前实例收到信号,使用 TimeSpan 指定时间间隔。(继承自 WaitHandle) | 
| WaitOne(TimeSpan, Boolean) | 阻止当前线程,直到当前实例收到信号,使用 TimeSpan 指定时间间隔,并指定是否在等待之前退出同步域。(继承自 WaitHandle) | 
显式接口实现
| IDisposable.Dispose() | 此 API 支持产品基础结构,不能在代码中直接使用。 释放 WaitHandle使用的所有资源。(继承自 WaitHandle) | 
扩展方法
| GetAccessControl(EventWaitHandle) | 返回指定  | 
| SetAccessControl(EventWaitHandle, EventWaitHandleSecurity) | 设置指定事件等待句柄的安全描述符。 | 
| GetSafeWaitHandle(WaitHandle) | 获取本机操作系统等待句柄的安全句柄。 | 
| SetSafeWaitHandle(WaitHandle, SafeWaitHandle) | 设置本机操作系统等待句柄的安全句柄。 | 
适用于
线程安全性
此类是线程安全的。
另请参阅
- WaitHandle
- 托管线程处理
- 同步基元 概述