Skip to content

Instantly share code, notes, and snippets.

@olbrichj
Created June 19, 2018 17:58
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save olbrichj/7881150dda5d8a7399ff98dbc1741bc9 to your computer and use it in GitHub Desktop.
Save olbrichj/7881150dda5d8a7399ff98dbc1741bc9 to your computer and use it in GitHub Desktop.
class Account: NSObject {
var balance: Double
var id: Int
override init(id: Int, balance: Double) {
self.id = id
self.balance = balance
}
func withdraw(amount: Double) {
balance -= amount
}
func deposit(amount: Double) {
balance += amount
}
}
let a = Account(id: 1, balance: 1000)
let b = Account(id: 2, balance: 300)
DispatchQueue.global(qos: .background).async {
transfer(from: a, to: b, amount: 200)
}
DispatchQueue.global(qos: .background).async {
transfer(from: b, to: a, amount: 200)
}
func transfer(from: Account, to: Account, amount: Double) {
from.synchronized(lockObj: self) { () -> T in
to.synchronized(lockObj: self) { () -> T in
from.withdraw(amount: amount)
to.deposit(amount: amount)
}
}
}
extension NSObject {
func synchronized<T>(lockObj: AnyObject!, closure: () throws -> T) rethrows -> T
{
objc_sync_enter(lockObj)
defer {
objc_sync_exit(lockObj)
}
return try closure()
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment