Swift4新特性介绍2(下标支持泛型,Codable序列化)

原文 http://www.hangge.com/blog/cache/detail_1824.html

下标支持泛型

下标的返回类型支持泛型

有时候我们会写一些数据容器,Swift 支持通过下标来读写容器中的数据。但是如果容器类中的数据类型定义为泛型,过去下标语法就只能返回 Any,在取出值后需要用 as? 来转换类型。现在 Swift4 定义下标也可以使用泛型了。

struct GenericDictionary<Key: Hashable, Value> {
    private var data: [Key: Value]
     
    init(data: [Key: Value]) {
        self.data = data
    }
     
    subscript<T>(key: Key) -> T? {
        return data[key] as? T
    }
}
 
//字典类型: [String: Any]
let earthData = GenericDictionary(data: ["name": "Earth", "population": 7500000000, "moons": 1])
 
//自动转换类型,不需要在写 "as? String"
let name: String? = earthData["name"]
print(name)
 
//自动转换类型,不需要在写 "as? Int"
let population: Int? = earthData["population"]
print(population)

下标类型同样支持泛型

extension GenericDictionary {
    subscript<Keys: Sequence>(keys: Keys) -> [Value] where Keys.Iterator.Element == Key {
        var values: [Value] = []
        for key in keys {
            if let value = data[key] {
                values.append(value)
            }
        }
        return values
    }
}
 
// Array下标
let nameAndMoons = earthData[["moons", "name"]]        // [1, "Earth"]
// Set下标
let nameAndMoons2 = earthData[Set(["moons", "name"])]  // [1, "Earth"]

Codable 序列化

如果要将一个对象持久化,需要把这个对象序列化。过去的做法是实现 NSCoding 协议,但实现 NSCoding 协议的代码写起来很繁琐,尤其是当属性非常多的时候。
Swift4 中引入了 Codable 协议,可以大大减轻了我们的工作量。我们只需要让需要序列化的对象符合 Codable 协议即可,不用再写任何其他的代码。

struct Language: Codable {
    var name: String
    var version: Int
}

Encode 操作

我们可以直接把符合了 Codable 协议的对象 encode 成 JSON 或者 PropertyList。

let swift = Language(name: "Swift", version: 4)
 
//encoded对象
let encodedData = try JSONEncoder().encode(swift)
 
//从encoded对象获取String
let jsonString = String(data: encodedData, encoding: .utf8)
print(jsonString)

Decode 操作

let decodedData = try JSONDecoder().decode(Language.self, from: encodedData)
print(decodedData.name, decodedData.version)

猜你喜欢

转载自blog.csdn.net/ZhangWangYang/article/details/85091779