NonblockingCondition
final public class NonblockingCondition<Environment> where Environment : ConcurrencyPlatform
extension NonblockingCondition: CustomDebugStringConvertible
Allows to wait for arbitrary predicates in non-blocking algorithms.
You can think of NonblockingCondition
as a condition variable, but the predicate to wait upon
does not need to be protected by a mutex. Using NonblockingCondition
in a non-blocking
algorithm (instead of spinning) allows threads to go sleep, saving potentially significant
amounts of CPU resources.
To use NonblockingCondition
, your algorithm should look like the following:
let nbc = NonblockingCondition(...)
// Waiting thread:
if predicate { return doWork() }
nbc.preWait(threadId)
if predicate {
nbc.cancelWait(threadId)
return doWork()
}
nbc.commitWait(threadId) // Puts current thread to sleep until notified.
// Notifying thread:
predicate = true
nbc.notify() // or nbc.notifyAll()
Notifying is cheap if there are no waiting threads. preWait and commitWait are not cheap, but they should only be executed if the preceding predicate check failed. This yields an efficient system in the general case where there is low contention.
-
Initializes NonblockingCondition for use by up to
threadCount
waiters.Declaration
Swift
public init(threadCount: Int)
-
Wakes up waiters.
notify
is optimized to be cheap in the common case where there are no threads to wake up.Declaration
Swift
public func notify(all: Bool = false)
-
Signals an intent to wait.
Declaration
Swift
public func preWait()
-
Cancels an intent to wait (i.e. the awaited condition occurred.)
Declaration
Swift
public func cancelWait()
-
Puts the current thread to sleep until a notification occurs.
Declaration
Swift
public func commitWait(_ threadId: Int)
-
Declaration
Swift
public var debugDescription: String { get }