Swift之map函数的强大之处

CollectionType Map

CollectionType的extension中map方法的定义:

extension CollectionType {
    /// Return an `Array` containing the results of mapping `transform`
    /// over `self`.
    ///
    /// - Complexity: O(N).
    @warn_unused_result
    @rethrows public func map<T>(@noescape transform: (Self.Generator.Element) throws -> T) rethrows -> [T]
    ...
}

@warn_unused_result:表示如果没有检查或者使用该方法的返回值,编译器就会报警告。

@noescape:用在函数的闭包参数上,意味着这个参数是唯一可被调用的(或者用在函数调用时以参数的方式出现),其意思是它的生命周期比函数调用的周期短,这有助于一些小小的性能优化,但最重要的是它屏蔽了闭包中对self.的需求。这使得函数的控制流比其他更加透明。

throws:可以抛出一个错误的函数或方法必需使用 throws 关键字标记。这些函数和方法被称为抛出异常函数(throwing fu nctions)和抛出异常方法(throwing methods)。

rethrows:一个函数或方法可以使用 rethrows 关键字来声明,从而表明仅当这个函数或方法的一个函数参数抛出错误时这个函数或方法才抛出错误。这些函数和方法被称为重抛出异常函数(rethrowing functions)和重抛出异常方法(rethrowing methods)。重抛出异常函数或方法必需有至少一个抛出异常函数参数。

Generator:提到数组我们就会想到遍历,一般的遍历可能都是从头到尾进行的。但是如果你有特殊的需求呢。你可能不想呆板的进行遍历。这时候Generators就可以派上用场了。Generators的存在是进行特殊癖好的数组遍历,其筛选出符合该癖好的下标索引到数组没有元素为止。Self.Generator.Element就是在遍历的元素。

简化一下map的定义:

func map<T>(transform: (Self.Generator.Element) -> T) -> [T]

可以看到,map 方法返回的是一个数组,其获取一个闭包表达式作为唯一参数,集合中的每个元素调用一次该闭包函数,并返回该元素所映射的值(也可以是不同类型的值)。具体的映射方式和返回值类型由闭包来指定。

看几个简单例子:

// 例子1:对一个Int类型数组的元素进行2倍放大。如:[1,2,3]->[2,4,6]。
let arr = [1,2,3]
let doubled = arr.map{
  $0 * 2
}
print(doubled)
// 输出:[2,4,6]
// 例子2:用一个Int类型数组存储商品金额,想把每个金额后面添加一个字符“¥”,把数组转成字符串数组。如:[10,20,30,40] -> ["10¥","20¥","30¥","40¥"]
let moneyArray = [10,20,30,40]
let stringsArray = moneyArray.map{
    "\($0)¥"
}
print(stringsArray)
// 输出:["10¥","20¥","30¥","40¥"]
// 例子3: 将Int类型数组转换为包含对应String类型的数。如:[16,58,510] -> ["OneSix", "FiveEight", "FiveOneZero"]。
let digitNames = [
                  0: "Zero",1: "One", 2: "Two",3: "Three", 4: "Four",
                  5: "Five", 6: "Six", 7: "Seven", 8: "Eight", 9: "Nine"
                 ]
let numbers = [16, 58, 510]

let strings = numbers.map{
    (var number) -> String in
    var output = ""
    while number > 0 {
        output = digitNames[number % 10]! + output
        number /= 10
    }
    return output
}
print(strings)
// 输出:["OneSix", "FiveEight", "FiveOneZero"]

想要了解更多map,看这里Why coding like This ------ Map 函数揭秘

Optional Map

以下内容出自《Swifter》

假设要将某个Int?乘以2,一个合理的策略是如果这个Int?有值的话,就取出值进行乘以2的操作,如果是nil赋给结果。代码如下:

let num: Int? = 3
var result: Int?
if let realNum = num {
    result = realNum * 2
} else {
    result = nil
}

其实我们有更优雅简洁的方式,那就是使用Optionalmap。对的,不仅仅在Array或者说CollectionType里可以用map,如果我们仔细看过Optional的声明的话,会发现它也有一个map方式:

public enum Optional<Wrapped> : _Reflectable, NilLiteralConvertible {
    ...
    /// If `self == nil`, returns `nil`.  Otherwise, returns `f(self!)`.
    @warn_unused_result
    @rethrows public func map<U>(@noescape f: (Wrapped) throws -> U) rethrows -> U?
    ...
}

这个方法能让给我们很方便的对一个Optional值做变化和操作,而不必进行手动的解包工作。输入会被自动用类似Optional Binding的方式进行判断,如果有值,则进入f的闭包进行变化,并返回一个U?;如果输入就是nil的话,则直接返回nilU?

有了这个方法,上面的代码就可以大大简化,而且result甚至可以使用常量值:

let num: Int? = 3
let result = num.map{
    $0 * 2
}
// result 为 {Some 6}

文/i红人(简书作者)
原文链接:http://www.jianshu.com/p/449cfe1b8fbb
著作权归作者所有,转载请联系作者获得授权,并标注“简书作者”。

时间: 2024-10-07 01:35:37

Swift之map函数的强大之处的相关文章

hdu 2112 HDU Today &lt;迪杰斯特拉算法+map函数&gt;

HDU Today Time Limit: 15000/5000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 19697    Accepted Submission(s): 4635 Problem Description 经过锦囊相助,海东集团终于度过了危机,从此,HDU的发展就一直顺风顺水,到了2050年,集团已经相当规模了,据说进入了钱江肉丝经济开发区500强.这时候

Swift高阶函数:Map,Filter,Reduce

闭包介绍 Swift一大特性便是使用简洁的头等函数/闭包语法代替了复杂的blocks语法.希望我们在Swift中不再需要像fuckingblocksyntax中所描述的语法.(译者注:头等函数-即可将函数当作参数传递给其他的函数,或从其他的函数里返回出值,并且可以将他们设定为变量,或者将他们存储在数据结构中) 闭包是自包含的blocks,它能在代码中传递和使用. 本文我们将重点介绍匿名定义的闭包(如:定义成内联的且不具名)也称匿名闭包.我们能够将其作为参数传递给其他函数/方法或者将其作为返回值.

Swift高阶函数介绍(闭包、Map、Filter、Reduce)

Swift语言有非常多函数式编程的特性.常见的map,reduce,filter都有,初看和python几乎相同,以下简介下 闭包介绍: 闭包是自包括的功能代码块,能够在代码中使用或者用来作为參数传值. 如果我们须要两个函数,当中一个计算两个数的平方的平均值,还有一个计算两个数的立方的平均值,传统的解决方法会是这样: 代码func square(a:Float) -> Float { return a * a}func cube(a:Float) -> Float { return a * a

理解Swift中map 和 flatMap对集合的作用

map和flatMap是函数式编程中常见的概念,python等语言中都有.借助于 map和flapMap 函数可以非常轻易地将数组转换成另外一个新数组. map函数可以被数组调用,它接受一个闭包作为參数,作用于数组中的每一个元素.闭包返回一个变换后的元素.接着将全部这些变换后的元素组成一个新的数组. 简单的说. map就是映射函数,把一个集合映射成还有一个集合. Swift的flatMap不easy理解,flatMap非常像map函数,可是它摒弃了那些值为nil的元素. flatMap是在处理一

PAT甲题题解-1038. Recover the Smallest Number (30)-排序/贪心,自定义cmp函数的强大啊!!!

博主欢迎转载,但请给出本文链接,我尊重你,你尊重我,谢谢~http://www.cnblogs.com/chenxiwenruo/p/6789138.html特别不喜欢那些随便转载别人的原创文章又不给出链接的所以不准偷偷复制博主的博客噢~~ 题意:给出n个数,求拼接后值最小的数是多少. 一开始就简单的把所有字符串先从小到大拍个序,然后拼接起来去掉前导零,结果发现有个问题,比如下面两个32 32321如果按常规字符串比较,32是在32321前面.然而,32321-32才是较小的方案如何有个好的比较

python之eval函数,map函数,zip函数

eval(str)函数很强大,官方解释为:将字符串str当成有效的表达式来求值并返回计算结果.所以,结合math当成一个计算器很好用. eval()函数常见作用有: 1.计算字符串中有效的表达式,并返回结果 >>> eval('pow(2,2)') 4 >>> eval('2 + 2') 4 >>> eval("n + 4") 85 2.将字符串转成相应的对象(如list.tuple.dict和string之间的转换) >&g

学习JQuery中文文档之map()函数和get()函数

今天学到一个新的函数map(). map(callback) 官方概述: 将一组元素转换成其他数组(不论是否是元素数组) 你可以用这个函数来建立一个列表,不论是值.属性还是CSS样式,或者其他特别形式.这都可以用'$.map()'来方便的建立. 参数: 给每个元素执行的函数 为了让学习者更容易理解这个函数,于是就有了下面这个栗子: <!DOCTYPE html> <html lang="en"> <head> <meta charset=&qu

【Swift】Map、FlatMap、CompactMap、CompactMapValues、Filter、Reduce

Map map函数能够被数组调用,它接受一个闭包作为参数,作用于数组中的每个元素.闭包返回一个变换后的元素,接着将所有这些变换后的元素组成一个新的数组 1. 比如我们有一个这样的需求遍历一个数组中所有的元素,将每个元素自身与自身相加,最后返回一个保存相加后元素的数组(-_-原谅我这表达能力,下面用代码阐述) 如果我们不使用map函数,那么代码如下 let numbers = [1,2,3] var sumNumbers = [Int]() for var number in numbers {

python之Map函数

# map()函数使用举例 # 功能:map()接受一个函数f和一个或多个list,将f依次作用在list的每个元素,得到一个新的列表 # 语法:map(方法名,列表,[列表2]) # 注意:map()函数的返回值需要强制转换成list类型,且不改变原列表值 list_1 = [1, 2, 3, 4, 5] list_2 = [1, 2, 3, 4, 5] # 单个参数 def double_function(number): return number * 2 list_result = li