Безопасно ли сигнализировать и немедленно закрыть ManualResetEvent?

Я чувствую, что должен знать ответ на этот вопрос, но я все равно спрошу на всякий случай, если сделаю потенциально катастрофическую ошибку.

Следующий код выполняется должным образом без ошибок / исключений:

static void Main(string[] args)
{
    ManualResetEvent flag = new ManualResetEvent(false);
    ThreadPool.QueueUserWorkItem(s =>
    {
        flag.WaitOne();
        Console.WriteLine("Work Item 1 Executed");
    });
    ThreadPool.QueueUserWorkItem(s =>
    {
        flag.WaitOne();
        Console.WriteLine("Work Item 2 Executed");
    });
    Thread.Sleep(1000);
    flag.Set();
    flag.Close();
    Console.WriteLine("Finished");
}

Конечно, как это обычно бывает с многопоточным кодом, успешное тестирование не доказывает, что это на самом деле потокобезопасно. Тест также будет успешным, если я поставлюClose доSet, хотя в документации четко указано, что попытка сделать что-либо послеClose приведет к неопределенному поведению.

Мой вопрос, когда я призываюManualResetEvent.Set метод, это гарантирует сигналвсе ожидающие темыдо вернуть контроль звонящему? Другими словами, при условии, что я могу гарантировать, что больше не будет звонковWaitOne, безопасно ли здесь закрывать дескриптор, или возможно, что при некоторых обстоятельствах этот код будет препятствовать тому, чтобы официанты получили сигнал, или приведет кObjectDisposedException?

Документация только говорит, чтоSet переводит его в «сигнальное состояние» - он, кажется, не претендует на то, когда официантына самом деле получить этот сигнал, так что я хотел бы быть уверен.

Ответы на вопрос(4)

Ваш ответ на вопрос