Swift學習筆記之閉包

來源:互聯網
上載者:User

標籤:func   大致   rar   總結   記憶體管理   ber   www   pre   alias   

簡介 (真的很簡)

閉包的完整形態是這個樣子的:

    { (parameters) -> returnType in        statements    }

寫在一行裡就是這樣:

    {(parameters) -> (returnType) in statements}
形式

閉包以三種形式存在:

1.全域的函數都是閉包,它們有自己的名字,但是沒有捕獲任何值。2.內嵌的函數都是閉包,它們有自己的名字,而且從包含他們的函數裡捕獲值。3.閉包運算式都是閉包,它們沒有自己的名字,通過輕量級的文法定義並且可以從上下文中捕獲值。
捕獲值

閉包可以捕獲內容相關的值,然後把它儲存下來。至於儲存的是引用還是拷貝,Swift 會決定捕獲引用還是拷貝值,也會處理變數的記憶體管理操作。

下面這個例子可以說明很多問題:

    func makeIncrementor(forIncrement amount: Int) -> () -> Int {        var runningTotal = 0        func incrementor() -> Int {            runningTotal += amount            return runningTotal        }        return incrementor    }    let incrementByTen = makeIncrementor(forIncrement: 10)    incrementByTen()    // runningTotal = 10    incrementByTen()    // runningTotal = 20    incrementByTen()    // runningTotal = 30    let incrementByTen2 = makeIncrementor(forIncrement: 10)    incrementByTen2()    // runningTotal = 10    let incrementByTen3 = incrementByTen    incrementByTen()    // runningTotal = 40

因為 incrementByTen2 聲明了一個全新的閉包,所以 runningTotal 並沒有繼續接著上面的計數。而 incrementByTen3 和 incrementByTen 指向的是同一個閉包,所以 runningTotal 的值是累加的。

參數縮寫

我們可以直接用 $0 $1 $2 這種來依次定義閉包的參數。比如 sorted 函數:

    var reversed = sorted(["c","a","d","b"], { $0 > $1 })   // d c b a
尾隨閉包

我一直覺得閉包最後這個 }) 很難看,在 JS 中隨處可見這種情況。如果閉包是函數的最後一個參數,Swift 提供了尾隨閉包 (Trailing Closures) 解決這個審美問題:

    // 以下是不使用尾隨閉包進行函數調用    someFunc({        // 閉包主體部分    })    // 以下是使用尾隨閉包進行函數調用    someFunc() {      // 閉包主體部分    }

OK那麼前面那個排序的可以用尾隨閉包這麼改寫:

    var reversed = sorted(["c","a","d","b"]) { $0 > $1 } // d c b a

如果除了閉包沒有其他參數了,甚至可以把小括弧也去掉。

還記得我們前面寫的 map 、 reduce 、 filter 三元大將嗎?用尾隨閉包可以讓它們變得更好看。比如前面那個選出大於30的數位 filter 就可以這樣寫:

    var oldArray = [10,20,45,32]    var filteredArray  = oldArray.filter{        return $0 > 30    }    println(filteredArray) // [45, 32]
變形

變形金剛神馬的最有愛了。總結一下 closure 的變形大致有以下幾種形態:

    [1, 2, 3].map( { (i: Int) ->Int in return i * 2 } )    [1, 2, 3].map( { i in return i * 2 } )    [1, 2, 3].map( { i in i * 2 } )    [1, 2, 3].map( { $0 * 2 } )    [1, 2, 3].map() { $0 * 2 }    [1, 2, 3].map { $0 * 2 }
對比

通過 UIView 的 animateWithDuration 方法對 block 和 closure 進行簡單的對比。

block 版本:    [UIView animateWithDuration:1 animations:^{        // DO SOMETHING    } completion:^(BOOL finished) {        NSLog(@"OVER");    }];closure 版本:    UIView.animateWithDuration(1, animations: { () in         // DO SOMETHING        }, completion:{(Bool)  in            println("OVER")        })

可以看到原來的 ^ 符號已經不複存在,取而代之的是加在參數和傳回值後面的 in 。注意,如果有 in 的話,就算沒有參數沒有傳回值也一定需要 () ,否則會報錯。
總結

和 Objective-C 的 FuckingBlock 一樣,Swift 出來之後 FuckingClosure 也就應運而生。總結了 Closure 的常用文法和格式:

    // 作為變數    var closureName: (parameterTypes) -> (returnType)    // 作為可選類型的變數    var closureName: ((parameterTypes) -> (returnType))?    // 做為一個別名    typealias closureType = (parameterTypes) -> (returnType)    // 作為函數的參數    func({(parameterTypes) -> (returnType) in statements})    // 作為函數的參數    array.sort({ (item1: Int, item2: Int) -> Bool in return item1 < item2 })    // 作為函數的參數 - 隱含參數類型    array.sort({ (item1, item2) -> Bool in return item1 < item2 })    // 作為函數的參數 - 隱含傳回型別    array.sort({ (item1, item2) in return item1 < item2 })    // 作為函數的參數 - 尾隨閉包    array.sort { (item1, item2) in return item1 < item2 }    // 作為函數的參數 - 通過數字表示參數    array.sort { return $0 < $1 }    // 作為函數的參數 - 尾隨閉包且隱含傳回型別    array.sort { $0 < $1 }    // 作為函數的參數 - 引用已存在的函數    array.sort(<)
References
  • Closures
  • Closure Expressions in Swift
  • Fucking Closure
  • Writing completion blocks with closures in Swift
  • Enough About Swift Closures to Choke a Horse
  • Functions and Closures in Swift
  • Swift How-To: Writing Trailing Closures

 

  知識來源:http://lib.csdn.net/article/swift/474

Swift學習筆記之閉包

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.