假设封装一个缓存工具类,通过字典存放数据,假设在多线程中存储数据,那么就有必要加锁,保证数据的安全
1.DispatchSemaphore信号量
public struct Cache{
private static var data = [String: Any]()
public static func get(_ key: String) -> Any? {
data[key]
}
// value=2 代表"同时"可以有2条线程可以访问
private static var lock = DispatchSemaphore.init(value: 1)
public static func set(_ key: String, value: Any) {
// 加锁
lock.wait()
// 更严谨的做法使用defer代码块
defer { // 不管有没异常,最后都解锁
lock.signal()
}
data[key] = value
// 一旦执行的代码抛出异常,那么将永远无法解锁
// lock.signal()
}
}
2.NSLock示例
public struct Cache{
private static var data = [String: Any]()
public static func get(_ key: String) -> Any? {
data[key]
}
private static var lock = NSLock()
public static func set(_ key: String, value: Any) {
// 加锁
lock.lock()
defer { // 不管有没异常,最后都解锁
lock.unlock()
}
data[key] = value
}
}
3.NSRecursiveLock递归锁,使用方法同NSLock一样,
public struct Cache{
private static var data = [String: Any]()
public static func get(_ key: String) -> Any? {
data[key]
}
// 递归锁
private static var lock = NSRecursiveLock()
public static func set(_ key: String, value: Any) {
// 加锁
lock.lock()
defer { // 不管有没异常,最后都解锁
lock.unlock()
}
// 假设这里使用递归方法,又调用了set方法,必须要使用递归锁
data[key] = value
}
}