swift闭包-备
我给Swift 中的闭包一个定义:闭包是自包含的匿名函数代码块,可以作为表达式、函数参数和函数返回值,闭包表达式的运算结果是一种函数类型。
Swift中的闭包类似于Objective-C中的代码块、Java中的匿名内部类。
使用闭包表达式
Swift中的闭包表达式很灵活,其标准语法格式如下:
{ (参数列表) ->返回值类型 in
语句组
}
其中,参数列表与函数中的参数列表形式一样,返回值类型类似于函数中的返回值类型,但不同的是后面有in关键字。
Swift提供了多种闭包简化写法,我来介绍下面几种不同形式:
1、类型推断简化
类型推断是Swift的强项,Swift可以根据上下文环境推断出参数类型和返回值类型。以下代码是标准形式的闭包:
{(a:Int, b:Int) -> Intin
return a + b
}
Swift能推断出参数a和b是Int类型,返回值也是Int类型。简化形式如下:
{(a, b) in return a + b }
{a, b in return a + b } //参数列表括号也可以省略
2、隐藏return关键字
在闭包内部语句组只有一条语句,如return a + b等,那么这种语句都是返回语句。前面的关键字return可以省略,省略形式如下:
{a, b in a + b }
使用这种简化方式修改后的示例代码如下:
- func calculate(opr :String)-> (Int,Int)-> Int {
- var result : (Int,Int)-> Int
- switch (opr) {
- case "+" :
- result = {a, b in a + b } //return关键字省略了
- default:
- result = {a, b in a - b } //return关键字省略了
- }
- return result
- }
省略的前提是闭包中只有一条return语句。
3、省略参数名称
Swift提供了参数名省略功能,我们可以用$0、$1、$2…来指定闭包中参数,$0指代第一个参数,$1指代第二个参数,$2指代第三个参数,以此类推$n+1指代第n个参数。
使用参数名省略功能,在闭包中必须省略参数列表定义,Swift能够推断出这些缩写参数的类型。参数列表省略了,in关键字也需要省略。参数名省略之后如下所示:
{$0 + $1}
使用参数名省略后的示例代码如下:
- func calculate(opr :String)-> (Int,Int)-> Int {
- var result : (Int,Int)-> Int
- switch (opr) {
- case "+" :
- result = {$0 + $1} //采用了参数名省略
- default:
- result = {$0 - $1} //采用了参数名省略
- }
- return result
- }
- let f1:(Int,Int)-> Int = calculate("+")
- print("10 + 5 = \(f1(10,5))")
- let f2:(Int,Int)-> Int = calculate("-")
- print("10 - 5 = \(f2(10,5))")
4、使用闭包返回值
闭包表达本质上是函数类型,是有返回值的,我们可以直接在表达式中使用闭包的返回值。重新修改add和sub闭包,示例代码如下:
- let c1:Int = {(a:Int, b:Int) -> Int in
- return a + b
- }(10,5)
- print("10 + 5 = \(c1)")
解释:给c1赋值,后面是一个闭包表达式。但是闭包表达式不能直接赋值给c1,因为c1是Int类型,需要闭包的返回值。这就需要在闭包结尾的大括号后面接一对小括号(10,5),通过小括号(10,5)为闭包传递参数。
闭包表达式可以作为函数的参数传递,如果闭包表达式很长,就会影响程序的可读性。尾随闭包是一个书写在函数括号之后的闭包表达式,函数支持将其作为最后一个参数调用。
下面我们来看一个示例代码:
- func calculate(opr: String, funN:(Int, Int) -> Int) {
- //最后一个参数funN是(Int,Int)-> Int函数类型,funN可以接收闭包表达式
- switch (opr) {
- case "+" :
- print("10 + 5 = \(funN(10,5))")
- default:
- print("10 - 5 = \(funN(10,5))")
- }
- }
- calculate("+", funN: {(a: Int, b: Int) -> Int in return a + b }) //调用
- calculate("+"){(a: Int, b: Int) -> Int in return a + b } //调用,这种形式就是尾随闭包
- calculate("+") { $0 + $1 } //调用,这种形式就是尾随闭包
需要注意的是,闭包必须是参数列表的最后一个参数,如果calculate函数采用如下形式定义:
func calculate(funN:(Int, Int) ->Int, opr:String) {
...
}
由于闭包表达式不是最后一个参数,那么调用calculate函数就不能使用尾随闭包写法的。
swift闭包-备的更多相关文章
- Swift闭包概念与常见使用场景总结
·Swift 闭包 闭包(Closures)是自包含的功能代码块,可以在代码中使用或者用来作为参数传值. Swift 中的闭包与 C 和 Objective-C 中的代码块(blocks)以及其他一些 ...
- Swift --闭包表达式与闭包(汇编分析)
在Swift中,可以通过func定义一个函数,也可以通过闭包表达式定义一个函数! 一.闭包表达式 概念 闭包表达式与定义函数的语法相对比,有区别如下: 去除了func 去除函数名 返回值类型添加了关键 ...
- swift 闭包循环引用
当使用闭包时,类本身持有self,然后又在闭包中访问了self或者self的属性,就会导致恶心额循环引用.swift提供的解决方法是在闭包中定义捕获列表,捕获列表是闭包想怎么引用捕获来的变量.例如下面 ...
- swift 闭包
闭包可以捕获和存储其所在上下文中任意常量和变量的引用. 这就是所谓的闭合并包裹着 这些常量和变量,俗称闭包. Swift标准库中提供了sort排序函数,sort函数的第二个参数是个闭包.和OC中的bl ...
- [ios][swift]使用swift闭包进行viewcontroller反向传值
闭包参考:http://c.biancheng.net/cpp/html/2285.html 闭包详解 传值参考:http://www.tuicool.com/articles/vy2uUz Sw ...
- swift 闭包简写实际参数名$0、$1等理解
Swift 自动对行内闭包提供简写实际参数名,你也可以通过 $0 , $1 , $2 等名字来引用闭包的实际参数值. 如果你在闭包表达式中使用这些简写实际参数名,那么你可以在闭包的实际参数列表中忽略对 ...
- Swift闭包(Closure)
语法: { (parameters) ->return type in statements} 实例:采用函数实现: let names =["Chris", "A ...
- swift闭包传值
不知道原理,就知道这么用的,皮毛上的那一点. 寻思着把以前的项目改成swift的,结果了,,, 反向传值 一. //类似于OC中的typedef typealias sendValueClosure= ...
- Swift 闭包表达式
闭包是功能性自包含模块,可以在代码中被传递和使用. Swift 中的闭包与 C 和 Objective-C 中的 blocks 以及其他一些编程语言中的 lambdas 比较相似. 闭包的形式主要有三 ...
随机推荐
- jboss部署应用
简单的部署应用. 第一种方法是直接写JSP代码,然后放到指定的WAR文件夹中. 第二种,是同时META-INF下的application.xml文件,然后用JAR -CF编成WAR,再集合JSP形成E ...
- Qt入门(4)——Qt常见控件
Qt提供了大量的内建控件及通用对话框可满足程序员的绝大部分要求.我们将对这些控件和对话框作一个大概的介绍. 1. QLabel 定义 QLabel* m_labelOrdered = newQLabe ...
- BZOJ2038: [2009国家集训队]小Z的袜子(hose) -- 莫队算法 ,,分块
2038: [2009国家集训队]小Z的袜子(hose) Time Limit: 20 Sec Memory Limit: 259 MBSubmit: 3577 Solved: 1652[Subm ...
- 《Node.js开发指南》知识整理
Node.js简介 Node是一个可以让JavaScript运行在服务器端的平台,抛弃了传统平台依靠多线程来实现高并发的设计思路,而采用单线程.异步式I/O.事件驱动式的程序设计模型. 安装和配置No ...
- SQL-Employees Earning More Than Their Managers
思路: 今天复习数据库突然想起来leetcode上数据库的题目,就找来做了 (1)给表取别名 格式见code,这在自身连接的时候是很有必要的 (2)自身连接 from语句后面相当于接了“一张表”,如果 ...
- 你需要知道的12个Git高级命令
众所周知,Git目前已经是分布式版本控制领域的翘楚,围绕着Git形成了完整的生态圈.学习Git,首先当然是学习Git的基本工作流.相比于SVN等传统版本控制系统来说,Git是专为分布式版本控制而生的强 ...
- 模拟Vue之数据驱动2
一.前言 在随笔“模拟Vue之数据驱动1”结尾处,我们说到如果监听的属性是个对象呢?那么这个对象中的其他属性岂不就是监听不了了吗? 如下: 倘若user中的name.age属性变化,如何知道它们变化了 ...
- script标签的位置
1.在我们编写代码的时候,会在页面内使用<script>标签来写JS,虽然理论上script标签的位置放在哪里可以,但是还是有一点区别的. 2.为什么很多人把script标签放在底部: 初 ...
- CSS3: box-sizing 属性的简单认识
定义和用法: box-sizing 属性允许您以特定的方式定义匹配某个区域的特定元素. 默认值:content-box; 继承性:无: css版本:css3 语法:box-sizing: conten ...
- NuGet学习笔记(2)——使用图形化界面打包自己的类库
上文NuGet学习笔记(1) 初识NuGet及快速安装使用说到NuGet相对于我们最重要的功能是能够搭建自己的NuGet服务器,实现公司内部类库的轻松共享更新.在安装好NuGet扩展后,我们已经能够通 ...