Swift中对UserDefaults的封装
Founddation中UserDefaults是一种很轻量化的本地化工具,实际开发中经常会使用,由于苹果中很多类库还没有用Swift重写,所以在Swift中用UserDefaults就显示不是很Swift,还是OC的感觉,所以我就想对UserDefaults进行一次封装,让它更Swift,用起来更方便.我最早由这种想法实在Swift2的时候,那时候就感觉用起来不是很方便了,但是没有多想,之后又看到了一篇文章传送门,它是用Swift中subscript的方法对NSUserDefaults进行了封装,Swift中,Dic[key],Array[index],都是使用了subscript方法.我就是参照这位外国友人的思路进行了封装.
[subscript] + 泛型 的方式
这是我最开始的设计思路,先看代码
protocol UserDefaultProtocol {
func getKey() -> String
}
enum DefaultsKey: String,UserDefaultProtocol {
case token
case name
case mobile
func getKey() -> String {
return self.rawValue
}
}
public let Defaults = UserDefaults.standard
extension UserDefaults {
subscript(key: UserDefaultProtocol) -> Fakegenericity {
return Fakegenericity(self, key.getKey())
}
subscript(key: UserDefaultProtocol) -> Any?{
get{
let genericity : Fakegenericity = self[key]
return genericity
}
set{
guard let newValue = newValue else {
removeObject(forKey: key.getKey())
return
}
switch newValue {
case let v as Double:
self.set(v, forKey: key.getKey())
case let v as Int:
self.set(v, forKey: key.getKey())
case let v as Bool:
self.set(v, forKey: key.getKey())
case let v as URL:
self.set(v, forKey: key.getKey())
default:
self.set(newValue, forKey: key.getKey())
}
}
}
///直接根据key取int double等 就算取不到 也会返回 0 当有要存储0的需求时候 会有问题 所以 用过根据 object 去数据转 nsnumer 判断number? 使取 bool int等类型时 没有值会返回nil
func numberForKey(_ key: String) -> NSNumber? {
return object(forKey: key) as? NSNumber
}
/// Returns `true` if `key` exists
func hasKey(key: UserDefaultProtocol) -> Bool {
return object(forKey: key.getKey()) != nil
}
func removeAll(){
for(key,_) in dictionaryRepresentation() {
removeObject(forKey: key)
}
}
func remove(key: UserDefaultProtocol){
removeObject(forKey: key.getKey())
}
class Fakegenericity {
fileprivate let defaults: UserDefaults
fileprivate let key: String
fileprivate init(_ defaults: UserDefaults, _ key: String) {
self.defaults = defaults
self.key = key
}
// MARK: only - get
public var object: Any? {
return defaults.object(forKey: key)
}
public var string: String? {
return defaults.string(forKey: key)
}
public var array: [Any]? {
return defaults.array(forKey: key)
}
public var dictionary: [String: Any]? {
return defaults.dictionary(forKey: key)
}
public var data: Data? {
return defaults.data(forKey: key)
}
// public var date: Date? {
// return object as? Date
// }
public var number: NSNumber? {
return defaults.numberForKey(key)
}
public var int: Int? {
return number?.intValue
}
public var double: Double? {
return number?.doubleValue
}
public var bool: Bool? {
return number?.boolValue
}
public var stringValue: String {
return string ?? ""
}
public var arrayValue: [Any] {
return array ?? []
}
public var dictionaryValue: [String: Any] {
return dictionary ?? [:]
}
public var dataValue: Data {
return data ?? Data()
}
public var intValue: Int {
return int ?? 0
}
public var doubleValue: Double {
return double ?? 0
}
public var boolValue: Bool {
return bool ?? false
}
}
}