定义Model:
struct UserModel : HandyJSON {
var name : String?
var age : Int?
}
定义TabelView的数据源:
var listData :[UserModel] = []
let userModel_W = UserModel(name : "WY", age : 18)
let userModel_X = UserModel(name : "XY", age : 28)
let userModel_F = UserModel(name : "FY", age : 24)
listData.append(userModel_W)
listData.append(userModel_X)
listData.append(userModel_F)
map( _ :)
对集合中的每个元素进行转换,返回一个新的数组
如果想要在拿到只有name的数据源该怎么处理呢:
一般就是通过for循环把想要的数据添加进一个新的数组内
var nameData : [String] = []
for model in listData {
if let name = model.name {
nameData.append(name)
}
}
let nameArray : NSMutableArray = []
for model in listData {
if let name = model.name {
nameArray.add(name)
}
}
如果使用map()的高阶函数一切就变的简单了
let nameListData = listData.map( { $0.name } )
print("name===\(nameListData)")
//输出
name = [optional("WY"),optional("XY"),optional("FY")]
底层逻辑:
map()是通过以下的协议扩展实现的:
func map<T>(_ transform : (Element) throws -> T) rethrows -> [T]
// 该协议方法使用了T泛型来作为参数传入,返回一个使用泛型来作为值的数组
// 通过**(Element) throws -> T**闭包的形式用来抛出错误
// 闭包的返回值和函数的返回类型都是泛型(没有固定类型),在需要使用的时候来决定类型
map()的主要用于转换(transform)
大致的实现原理:
- 创建一个新的空数组,容量预分配为原集合的容量
- 遍历原集合的每个元素
- 对每个元素应用转换闭包
- 将转换结果追加到新数组中
- 返回新数组
其他功能:
因其传入的是泛型因此不仅仅能处理数组,也可以处理字典
// 对字典键值转换
let dict = ["a": 1, "b": 2, "c": 3]
let newDict = dict.map { ($0.key.uppercased(), $0.value * 2) }
// [("A", 2), ("B", 4), ("C", 6)]
// 取key值
let dict = ["a" : 1, "b" : 2, "c" : 3]
let keyData = dict.map {($0.key)}
//输出
keyData === ["b","a","c"]
// 输出的Key数组的顺序并不是固定的
// 类型转换
let strings = ["1", "2", "3"]
let numbers = strings.map { Int($0) } // [Int?]
// 条件转换
let numbers = [1, 2, 3, 4, 5]
let evenSquares = numbers.map { $0 % 2 == 0 ? $0 * $0 : $0 }
// [1, 4, 3, 16, 5]
compactMap(_:)
和map( _ :)的最大区别就是 map( _ :) 在对集合元素进行转换过程中并不会过滤掉nil值
let userModel_T = UserModel(name : nil, age : 24)
listData.append(userModel_T)
//分别进行map( _ :)和compactMap(_:)
let nameListData = listData.map( { $0.name } )
print("nameListData===\(nameListData)")
nameListData = [optional("WY"), optional("XY"), optional("FY"), nil]
let newData = listData.compactMap( { $0.name } )
print("newData===\(newData)")
newData = ["WY", "XY", "FY"]
从输出结果上可以看出有两大不同
- map( _ :)并不会过滤掉nil项,compactMap(_:) 则自动过滤了nil值
- map( _ :)的转过结果是可选值内容,而compactMap(_:)返回的是一个非可选值的新数组