views:

49

answers:

2

For me now it looks like functionally Semaphore.WaitOne/Release is equal to Monitor.Wait/Pulse. Skipping interprocess capabilities, speed (yes, Monitor is managed) other nonfunctional differences, what is real difference then?

+1  A: 

Monitor.Wait/Pulse provides you with a condition variable, which is more like an auto-reset event than a semaphore (but not exactly). The main difference is that a semaphore has a count, which means you don't need to lock anything in order to ensure you don't miss a pulse (unlike with Monitor.Wait).

wj32
+1  A: 

The main purpose of a Semaphore is to control access to a finite set of resources. Thread can participate in resouce acquisition by calling WaitOne and Release. A thead should call WaitOne to acquire the resource. However, it will only block if the semaphore's count reaches 0 otherwise the thread is free to acquire immediately. Once that thread is finished it should call Release to signal the semaphore that an extra slot has been freed up for another thread.

Monitor.Wait and Monitor.Pulse are drastically different. First and foremost there is no counting involved. If Pulse is called in the absence of any call to Wait then the signal is ignored and discarded. It is not queued up in the same way that a semaphore would. In fact, the behavior of Wait and Pulse has no inherent meaning at all. The Wait is simply waiting for a change in the state of the acquired lock (acquired from Monitor.Enter). The Pulse is the signal that something changed. That is why you often see Wait called in a while loop. The waiting thread must retest the wait condition because it has no idea what changed!

Monitor.Wait and Monitor.Pulse are fundamental synchronization mechanisms that can be used to form pretty much any other synchronization device including semaphores.

Brian Gideon
this is really awesome answer! it cleared things for me!
Andrey