闭包的主要意义是在一些场景中实现语法的优化,比如可以利用上下文来推断出参数和返回值的类型,而不需要像函数一样必须指定相应的参数类型和返回值类型,例如:在一些单独的表达式中闭包可以省略return的关键字,对于参数名也可以进行一定程度的简写,使得代码更加紧凑;
- 闭包的标准语写法
var arr:[Int] = [1,3,5,7,9,2,4,6,8,0]
arr.sorted()
func compareTwoInoInts(a:Int,b:Int)->Bool{
return a>b
}
arr.sorted(by: compareTwoInoInts)
//闭包和匿名函数有点类似
arr.sorted(by: {(a:Int,b:Int)->Bool in
return a>b
})
var strArr = ["d","cd","bcd","abcd","abc","ab","a"]
strArr.sorted(by: {(s1:String,s2:String)->Bool in
if s1.characters.count != s2.characters.count{
return s1.characters.count < s2.characters.count
}
return s1 < s2
})
- 闭包的简化写法
//闭包的简化式写法
//1、如果闭包的逻辑很简单,只有一句话时,可以不用换行写
arr.sorted(by: {(a:Int,b:Int)->Bool in return a>b})
//2、闭包具有根据上下文,根据当前的情况来推断传入的参数以及返回的参数的能力
arr.sorted(by: {a,b in return a>b})
//3、闭包中return这个关键字是可以省略的,面对比较复杂的情况还是不能省略的
arr.sorted(by: {a,b in a>b})
//4、参数名也是可以省略的
arr.sorted(by: {$0 > $1})
arr.sorted(by: >)
- Trailing Closure 结尾闭包
针对比较复杂的闭包逻辑,如果这个闭包是放在最后,在具体调用时可以将闭包写在函数的后面,即:
strArr.sorted(){ (s1,s2) in
if s1.characters.count != s2.characters.count{
return s1.characters.count < s2.characters.count
}
return s1 < s2
}
- Capturing Values 数值捕获
即闭包可以智能的去寻找在闭包的函数体中所使用的变量,如果发现它不是被传入的变量,则会向外一层去找相应的变量;
arr.sorted(){return fabs(Float($0 - 5)) < fabs(Float($1 - 5))}
//Capturing Values 数值捕获
var num = 3
arr.sorted(){return fabs(Float($0 - num)) < fabs(Float($1 - num))}
- 值类型和引用类型
- 值类型 Value Type
所谓的值类型,是指当它作为参数传入函数的时候,包括被赋值的时候所产生的是一个同类型的副本,例如:
var a:Int = 2
var b:Int = a
b //值为2
b+=1
b //3,操作b不会改变a
a //2
a-=1
a //1,操作a也不会改变b
b //3
Swift中的值类型包括:Int、Float、Double、Bool、Tuple、String、Array、Dictionary
注意:在很多其他语言中Array、Dictionary会被包装成类,是引用类型
- 引用类型 Reference Type
Swift中的引用类型:函数Function,闭包Closure
//引用类型,例如:
//参数:todayMiles,返回值:函数
func calcTotalMiles(todayMiles:Int) -> ()->Int{
var totalMiles = 0
//calcTotalMiles函数的返回值是个函数类型,这个函数的具体值是用闭包实现的,并且用到了数值捕获
return{ totalMiles += todayMiles; return totalMiles}
}
var dailyTwoMiles = calcTotalMiles(todayMiles: 2)
dailyTwoMiles() //2
dailyTwoMiles() //4
dailyTwoMiles() //6
var myPlan = dailyTwoMiles
myPlan() //8
dailyTwoMiles() //10