Swift:函數(shù)與閉包(block)

Functions and Closures

github:Swift基礎(chǔ)實(shí)例
github:SwiftBasicTableView

函數(shù)
  • 函數(shù)聲明
    func 聲明一個(gè)函數(shù),通過(guò)函數(shù)名來(lái)調(diào)用函數(shù),函數(shù)如果有參數(shù),在圓括號(hào) () 中需要跟上相應(yīng)參數(shù)。用符號(hào) -> 把函數(shù)的參數(shù)和函數(shù)的返回值類型隔開(kāi)。
var nameAndDay = ""
func greet(name: String, day: String, number: Int) ->String {
    return "Hello \(name), today is \(day), \(number)."
}
nameAndDay = greet("Swift", day: "Sunday", number: 1)
print(nameAndDay)
  • 輸出 Hello Swift, today is Sunday, 1.
  1. 函數(shù)返回多個(gè)值
    從函數(shù)返回多個(gè)值時(shí),可以使用元組 tuple ,通過(guò) 名字 或 索引來(lái)訪問(wèn) tuple 中的值:
func calculate(scores: [Int]) -> (min: Int, max: Int, sum: Int) {
    var min = scores[0]
    var max = scores[0]
    var sum = 0
    for score in scores {
        if score > max {
            max = score
        }
        else if score < min {
            min = score
        }
        sum += score
    }
    return (min,max,sum)
}
let statistics = calculate([5, 10, 39, 5])
print(statistics.sum)
print(statistics.1)
  1. 參數(shù)數(shù)量可變的函數(shù)
func sumOf(numbers:Int...) ->Int {
    var sum = 0
    // numbers.count
    for number in numbers {
        sum += number
    }
    return sum
}
print(sumOf())
print(sumOf(1,3,4,5))
  • 上面代碼中,一系列的參數(shù)放在了一個(gè)數(shù)組 numbers
  1. 函數(shù)嵌套
    嵌套函數(shù)中,內(nèi)層函數(shù)可以使用外層函數(shù)中的變量。一個(gè)函數(shù)中的代碼如果太長(zhǎng),或者比較復(fù)雜,那么可以使用嵌套函數(shù)來(lái)組織組織這些代碼:
func returnFifteen() ->Int {
    var y = 10
    func add() {
        y += 5
    }
    add()
    return y
}
print(returnFifteen())
  1. 返回函數(shù)
    Swift 的函數(shù)是第一類類型first-class type,這意味著一個(gè)函數(shù)可以把其他函數(shù)作為它的返回值:
func makeIncrementer() ->((Int)->Int) {
    func addOne(number:Int) ->Int {
        return 1 + number
    }
    return addOne
}
var increment = makeIncrementer()
print(increment(7))
  • 在函數(shù) makeIncrementer 中,構(gòu)造了另外一個(gè)函數(shù) addOne 并將其返回,返回函數(shù)名就可以(猜測(cè),可能返回的是函數(shù)指針)
  1. 函數(shù)作為參數(shù)
    一個(gè)函數(shù)可以作為另外一個(gè)函數(shù)的參數(shù),傳遞進(jìn)去:
func lessThanTen(number:Int) ->Bool {
    return number < 10
}
func hasAnyMatches(list:[Int], condition:(Int) ->Bool) ->Bool {
    
    for item in list {
        if condition(item) {
            return true
        }
    }
    return false
}
var numbers = [20,13,4,9]
hasAnyMatches(numbers, condition: lessThanTen)
  • 傳遞函數(shù)時(shí),也是只傳遞名稱就可以
閉包(block)

閉包格式

{ (參數(shù)) -> 返回值類型 in
    statements
}```
- 有名稱的閉包
函數(shù)是特殊的閉包:代碼塊可以稍后被調(diào)用。上面的嵌套函數(shù),就屬于是有名字的閉包,無(wú)名的閉包(`匿名閉包`)是不寫(xiě)名字(比如`函數(shù)名`),然后把代碼放在大括號(hào)`{}`中。再看下面的栗子:假設(shè)我們要寫(xiě)兩個(gè)函數(shù),一個(gè)計(jì)算兩個(gè)數(shù)的平方的平均值,一個(gè)計(jì)算兩個(gè)數(shù)的立方的平均值,一般做法是:

func square(a:Float) ->Float {
return aa
}
func cube(a:Float) ->Float {
return a
a*a
}
func averageSumOfSquare(a:Float, b:Float) ->Float {
return (square(a) + square(b))/2.0
}
func averageSumOfCube(a:Float, b:Float) ->Float {
return (cube(a) + cube(b)) / 2.0
}
averageSumOfSquare(1.0, b: 3.0)
averageSumOfCube(2.0, b: 3.0)

上面函數(shù) `averageSumOfSquare` 和 `averageSumOfCube` 唯一不同之處就是分別調(diào)用了平方函數(shù)和立方函數(shù)。如果我們可以定義這樣一個(gè)函數(shù),這個(gè)函數(shù)以兩個(gè)數(shù)和一個(gè)使用這兩個(gè)數(shù)的函數(shù)作為參數(shù),來(lái)計(jì)算平均值而不是重復(fù)調(diào)用將會(huì)非常好,我們可以使用閉包作為函數(shù)參數(shù):

func averageOfSum(a:Float, b:Float, f:(Float ->Float)) ->Float {
return (f(a) + f(b))/2.0
}
averageOfSum(2.0, b: 3.0, f: square)
averageOfSum(3.0, b: 3.0, f: cube)

   - `square`和`cube`可以被看做有名稱的閉包

2. 無(wú)名稱閉包
下面說(shuō)一下無(wú)名內(nèi)聯(lián)閉包,代碼也是寫(xiě)在大括號(hào) `{}` 中,代碼用 `in` 將參數(shù)和返回類型與實(shí)現(xiàn)(`body`)隔開(kāi):

// 注意格式,每一行換行的地方
individualScores.map({
(number:Int) ->Int in
let result = number+3
return result
})


3. 閉包簡(jiǎn)寫(xiě)
如果閉包的類型是已知的,比如 `delegate`,那么可以刪掉閉包的`參數(shù)類型`或`返回類型`,或者兩者都刪掉。單語(yǔ)句閉包隱式返回這條語(yǔ)句的執(zhí)行結(jié)果.

individualScores.map({
number in number+3})
print(individualScores)
let mappedScores = individualScores.map({
number in number+3})

   - 數(shù)組 `individualScores` 中的值沒(méi)有變化,而是調(diào)用 `.map` 之后會(huì)返回一個(gè)新的數(shù)組,新數(shù)組`mappedScores`中的值會(huì)每個(gè)都加3

   我們還可以忽略參數(shù)名,使用默認(rèn)參數(shù)名`$0`,如果有多個(gè)參數(shù),使用 `$n` 作為第 `n-1` 個(gè)參數(shù):

individualScores.map({
$0+3})

如果某一個(gè)函數(shù)的最后一個(gè)參數(shù)是閉包,那么這個(gè)閉包可以直接出現(xiàn)在圓括號(hào)`()`之后,例如下面的升序排序:

let sortedNumbers = individualScores.sort(){
$0 < $1
}
print(sortedNumbers)

如果某一個(gè)函數(shù)唯一的參數(shù)是閉包,那么可以把圓括號(hào)`()`省略掉:

let sortedNumbers = individualScores.sort {
$0 < $1
}
print(sortedNumbers)


4. 總結(jié)
>閉包是函數(shù)的一種,但閉包的真正意義是:把參數(shù)傳遞進(jìn)一個(gè)塊(這個(gè)塊是用來(lái)實(shí)現(xiàn)閉包的),然后對(duì)參數(shù)就行修改,修改過(guò)之后,再使用??偨Y(jié)為一句話,傳遞參數(shù)-->修改-->使用
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書(shū)系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容