Почему нет AutoResetEventSlim в BCL? - PullRequest
28 голосов
/ 21 ноября 2011

Почему в BCL нет класса AutoResetEventSlim?

Можно ли имитировать, используя ManualResetEventSlim?

Ответы [ 2 ]

27 голосов
/ 21 ноября 2011

ManualResetEvent и ManualResetEventSlim оба разработаны так, чтобы они оставались сигнальными после вызова.Как правило, это для сценария, совершенно отличного от AutoResetEvent.

AutoResetEvent, сразу после использования сразу возвращается в состояние без сигнала, что обычно используется для другого набора сценариев.Из документации AutoResetEvents:

Обычно этот класс используется, когда потокам необходим эксклюзивный доступ к ресурсу.

ManualResetEventSlim) обычно используются,однако для сценария, в котором:

это сообщение касается задачи, которую один поток должен завершить, прежде чем другие потоки смогут продолжить.

Поскольку AutoResetEvent чаще всего используется вВ сценариях, где есть несколько потоков, совместно использующих ресурс, время ожидания обычно не будет очень коротким.ManualResetEventSlim, однако, действительно предназначен только для случаев, когда вы заранее знаете, что время ожидания очень короткое.Если ваше время ожидания не будет очень коротким, тогда вы должны использовать ManualResetEvent.Подробности смотрите в документации по разнице между MRE и MRES .

Когда время ожидания больше (что было бы нормальным сценарием с AutoResetEvent), «тонкая» версияна самом деле хуже, так как он возвращается к использованию дескриптора ожидания.

13 голосов
/ 13 сентября 2014

Этот факт меня тоже прослушивал.Однако кажется, что вы можете смоделировать AutoResteEvent (Slim), используя простой SemaphoreSlim со специальной конфигурацией:

SemaphoreSlim Lock = new SemaphoreSlim( 1, 1 );

Первый параметр (http://msdn.microsoft.com/en-us/library/dd270891(v=vs.110).aspx) определяет начальное состояние семафора: 1 означаетчто один поток может войти, 0, что семафор должен быть освобожден первым.Таким образом, a = new AutoResetEvent( true ) переводит в = new SemaphoreSlim( 1, 1 ), а a = new AutoResetEvent( false ) переводит в = new SemaphoreSlim( 0, 1 ) соответственно.

Второй параметр определяет максимальное числоПотоки, которые могут одновременно входить в семафор. Установка его в 1 позволяет ему вести себя как AutoResetEvent.

Еще одна приятная вещь в SemaphoreSlim - то, что с новым шаблоном async / await в 4.5 класс получил.WaitAsync() метод, который можно ожидать. Таким образом, больше нет необходимости вручную создавать примитив ожидаемого ожидания в этом случае.

Надеюсь, это поможет.

...