【问题标题】:Questions on simple threading jargon [closed]关于简单线程术语的问题[关闭]
【发布时间】:2011-03-22 06:01:54
【问题描述】:
当手动重置事件发出信号时,
等待事件的所有线程
变得可调度。当自动复位
事件发出信号,只有其中之一
等待事件的线程变为
可调度。
由于我是线程新手,所以我有一些非常菜鸟的问题要问。
- “设置”和“重置”事件是什么意思?
- 手动重置和自动重置事件有什么区别?
- “发出信号”的事件是什么意思?是否表示已激活?
- 线程变为“可调度”是什么意思?
- 什么是“等待事件”?
【问题讨论】:
标签:
multithreading
terminology
【解决方案1】:
想想电灯开关。当事件被“发出信号”时,灯开关打开。当事件“重置”时,电灯开关关闭。
自动重置事件意味着在事件发出信号(打开)并释放线程后,事件会自动重置(关闭)。在手动重置(关闭)之前,手动重置事件会一直发出信号(打开)。
参见上面的#1。
当线程等待事件时,线程被阻塞,这意味着操作系统无法安排它工作。当线程正在等待的事件被设置(发出信号,打开)时,线程被释放,即变为可调度的。这仅仅意味着操作系统现在可以安排线程工作。
等待事件仅仅意味着调用事件的Wait() 函数之一。线程将“等待”直到事件被设置/发出信号/打开,然后再继续它的任何工作。
【解决方案2】:
基本上,“WaitHandle”(包括手动重置事件和自动重置事件)是允许线程等待直到发生某些事情的类型 - 在这种情况下,直到 WaitHandle 为“设置”。
线程(线程 A)可以在 WaitHandle 上“等待”,阻塞直到单独的线程(线程 B)“设置”(=="signals")WaitHandle。这将允许线程 A 在该点继续运行。
如果您有多个线程在 WaitHandle 上等待,那么主要的区别就出现了。在这种情况下,通过手动重置事件,所有线程都将被允许继续运行(即:它们现在是可调度的,这意味着操作系统将在某个时候设置它们并再次运行它们,通常相当快)。使用自动重置事件,允许一个线程继续,而 WaitHandle 被“重置”,这会阻止其他线程继续(直到 WaitHandle 再次发出信号,当下一个线程被“释放”时)。
【解决方案3】:
解决您的每个问题:
1) 当一个事件被重置时,这意味着现在可以向另一个等待该事件的线程发出信号。换句话说,现在正在休眠(阻塞)的线程可以被唤醒以进行工作。
2) 根据Event Objects (MSDN),
手动重置事件:一个事件对象,其状态保持为信号状态,直到由 ResetEvent 函数显式重置为非信号状态。发出信号后,可以释放任意数量的等待线程,或随后在其中一个等待函数中指定相同事件对象的线程。
自动重置事件:一个事件对象,其状态保持有信号直到释放单个等待线程,此时系统自动将状态设置为无信号。
如果没有线程在等待,则事件对象的状态保持信号状态。如果有多个线程在等待,则选择一个等待线程。不要假设先进先出 (FIFO) 顺序。内核模式 APC 等外部事件可以更改等待顺序。
所以基本上通过手动重置事件,您可以显式重置事件,触发任意数量的线程来执行。通过自动重置事件,操作系统保证在事件发出信号时只会执行单个线程。
3) 是的,当一个事件发出信号时,一个线程正在使用该事件来执行工作。任何其他试图访问(信号)该事件的线程都将被阻止。
4) 在这个上下文中,schedulable 意味着一个线程可以被执行。根据事件设置,操作系统会选择一个或多个等待事件的线程,并执行它们。
5) 等待事件意味着线程正在阻塞事件对象。阻塞时,线程不执行任何 CPU 周期,基本上被操作系统“置于睡眠状态”。