Swift閉包_7

閉包是自包含的函數(shù)代碼塊,可以在代碼中被傳遞和使用,swift中閉包與coc的代碼塊匿名函數(shù)比較相似

閉包可以捕獲和儲(chǔ)存其所在的上下文中的任意變量和常量的引用,被稱之為包裹常量和變量,Swift會(huì)為你管理在捕獲過(guò)程中涉及到的所有內(nèi)存操作

在上個(gè)章節(jié)介紹的全局和嵌套函數(shù)實(shí)際上也是特殊的閉包,閉包采取如下三種形式之一

  • 全局函數(shù)是一個(gè)有名字但不會(huì)捕獲任何值的閉包
  • 嵌套函數(shù)是一個(gè)有名字并可以捕獲其封閉函數(shù)域值的閉包
  • 閉包表達(dá)式是利用一個(gè)輕量級(jí)語(yǔ)法所寫的可以捕獲其上下文變量或者常量值的匿名閉包

常閉包基本表達(dá)式

//最簡(jiǎn)單的閉包,無(wú)參數(shù)無(wú)返回值
        /*
         如果沒(méi)有參數(shù),沒(méi)有返回值,可以
         */
        let b1 = {
            print("最簡(jiǎn)單的閉包")
        }
        
        b1()
        
        //帶參數(shù)的閉包,無(wú)返回值
        /*
         閉包中,參數(shù),返回值,實(shí)現(xiàn)代碼都寫在{}中
         需要使用一個(gè)關(guān)鍵字'in' 分隔定義和實(shí)現(xiàn)
         {形參列表 -> 返回值類型  in //實(shí)現(xiàn)代碼}
         
         如果沒(méi)有參數(shù),沒(méi)有返回值,可以省略,連 ‘in’都可以省略
         
         */
        
        let b2 = { (x : Int , y : Int) in
            
            print("帶參數(shù)的閉包 參數(shù)x:\(x)  y:\(y)")
        }
        b2(100, 200)//先打出b2 再打出’(‘ 就會(huì)有提示的
        
        
        //帶參數(shù),帶返回的閉包
        
        let b3 = {(x : Int , y : Int) -> Int in
            
            return x + y
        }
        print(b3(150, 150))
       

閉包表達(dá)式語(yǔ)法有如下的一般形式

{(parameters) -> returnType in
    statements
}

閉包的函數(shù)體部分有關(guān)鍵字in引入,該關(guān)鍵字表示閉包的參數(shù)與返回值類型已經(jīng)定義完成,閉包函數(shù)體即將開(kāi)始

soret方法

swift標(biāo)準(zhǔn)庫(kù)提供了名為sorted(by:)的方法,它會(huì)根據(jù)你所提供的用于排序的閉包函數(shù)將已知類型的數(shù)組中的值進(jìn)行排序,一旦排序完成,sorted(by:)方法會(huì)返回一個(gè)與原數(shù)組大小相同,包含同類型且元素已正確排序的新數(shù)組,原數(shù)組不會(huì)被sorted(by:)方法

       let names = ["Chris","Alex","Ewar","Barry", "Daniella"]
        //let sortedNames2 = names.sorted(by: { (s1: String, s2: String) -> Bool in return s1 > s2 } )
        let sortedNames = names.sorted { (str1, str2) -> Bool in
            return str1 > str2
        }
        
        print("排序后的數(shù)組\(sortedNames)")
        //result:排序后的數(shù)組["Ewar", "Daniella", "Chris", "Barry", "Alex"]

根據(jù)上下文推斷類型

因?yàn)榕判蜷]包函數(shù)作為sorted(by:)方法的參數(shù)傳入的,swift可以推斷其參數(shù)與返回值的類型,sorted(by:)方法被一個(gè)字符串?dāng)?shù)組調(diào)用,因此其參數(shù)必須是(String ,String) -> bool類型的函數(shù),這意味著(String,String)bool 并不需要作為閉包表達(dá)式定義的一部分,因?yàn)樗械念愋投伎梢员徽_推斷,返回箭頭->和圍繞在參數(shù)周圍的括號(hào)也可以被省略

單表達(dá)式閉包隱式返回

單行表達(dá)式閉包可以通過(guò)省略return

let sortedNames3 = names.sorted { (str1, str2) -> Bool in str1 > str2}

參數(shù)名稱所寫

swift自動(dòng)為內(nèi)聯(lián)閉包提供了參數(shù)名稱所寫功能,你可以直接通過(guò)$0,$1``$2來(lái)順序調(diào)用閉包的參數(shù),以此類推

如果你在閉包表達(dá)式中使用參數(shù)名稱所寫,你可以在閉包定義中省略參數(shù)列表,并且對(duì)應(yīng)參數(shù)名稱所寫的類型會(huì)通過(guò)函數(shù)的類型推斷,in關(guān)鍵字也可以同樣被省略,因?yàn)榇藭r(shí)閉包表達(dá)式完全由閉包函數(shù)體構(gòu)成

let sortedNames4 = names.sorted { $0>$1 }

尾隨閉包

如果你需要將一個(gè)很長(zhǎng)的閉包表達(dá)式作為最后一個(gè)參數(shù)傳遞給函數(shù),可以使用尾隨閉包來(lái)增強(qiáng)函數(shù)的可讀性,
如果函數(shù)的最后一個(gè)參數(shù)是閉包,函數(shù)參數(shù)可以提前結(jié)束,最后一個(gè)參數(shù)直接使用{}包裝閉包的代碼

//函數(shù)
 func endClosure(closure:()->Void) -> Void {
        
        
        print("尾隨閉包");
        closure()
    }

//  調(diào)用
//使用尾隨閉包
        endClosure {
            print("尾隨閉包2")
        }
      
        //不使用尾隨閉包
        endClosure(closure:{
            print("尾隨閉包3")
        } )

值捕獲

閉包可以在其定義的上下文中捕獲常量或變量,即使定義這些常量和變量的員作用域已經(jīng)不存在,閉包仍然可以在閉包函數(shù)體內(nèi)引用和修改這些值
swift中,可以捕獲值的閉包的最簡(jiǎn)單形式就是嵌套函數(shù),也就是定義在其他函數(shù)體內(nèi)的函數(shù),嵌套函數(shù)可以捕獲其外部函數(shù)所有的參數(shù)已經(jīng)定義的常量和變量

//捕獲值的閉包的最簡(jiǎn)單形式是嵌套函數(shù)
    func moreFun(oriValue : Int) -> Int {
        
        var count = 10
        
        func inFunc() -> Int{
            
            count += oriValue
            return count
        }
        
        return inFunc()
    }

逃逸閉包

自動(dòng)閉包

?著作權(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)容