Swift學習(2函數閉包)

來源:互聯網
上載者:User

標籤:八卦   關心   方式   變化   寫法   exe   sleep   指標   sum   

函數的定義

1.函數的基礎寫法

func 函數名(形參列表)->傳回值類型

例: func sum(x:int ,y:int) -> int{

return x+y

}

print(sun(x:10,y:50))

 

2.外部參數的使用,就是在形參前加一個名字,外部參數不會影響函數內部細節,外部參數會讓外部調用看起來更加的直觀

例:func sum(num1 x:int ,num2 y:int )-> int{

return x+y

}

print(sum(num1:30,num2:40))

使用“_”可以替代不關心的展示方式,常見的還有for迴圈中”i”如果沒有用到的情況向,可以用“_”代替

func sun(_ x:int ,_ y:int )-> int{

return x+y

}

print(sum(30,40))

 

3.預設值:通過給參數設定預設值,在調用的時候,可以任意組合參數,如果不指定就使用預設值。但是在OC中是不能實現的,需要定義多個函數

例 :func sum(x:int=1,y:int=2)-> int{

return x+y

}

print(sum())

print(sum(x:10,y:10))

print(sum(x:10))

 

4.無傳回值的情況:主要用在閉包

例: func demo() {}

func demo1() ->() {}

func demo2() ->void {}

 

閉包

1.閉包的定義:類似於OC的block,但是比block應用更廣泛

OC中block是匿名的函數

swift中函數是特殊的閉包

1.提前準備好的代碼

2.在需要的時候執行

3.可以當做參數傳遞

例1:OC中是不能實現的函數賦值

func sum(x:int=1,y:int=2)-> int{

return x+y

}

let f = sum

print(f(x:20,y:40))

 

例2:簡單的閉包

沒有參數和傳回值的函數b1 (此情況下可以省略參數和傳回值,包括”in”)

let b1 = {

print(“hello word”)

}

執行閉包

b1()

例3:帶參數的閉包

閉包中,參數,傳回值,實現代碼都是寫在{}中

{形參列表->傳回值 in 實現代碼}

需要用 “in” 來分割定義和實現

let b2 = {

(x:int) ->() in

print(x)

}

b2(100)

例4:帶參數和傳回值的閉包

let b3 = {

(x:int) -> int in

return x+200

}

print(b3(1111))

 

2.swift中GCD的使用方法

1.GCD:將任務添加到隊列,指定執行任務的函數

2.翻譯:隊列調度任務(block/閉包),以同步/非同步 的方式來執行

例:func loadData() ->(){

DispatchQueue.global().async{

print(“耗時操作 \(Thread.current())”)

DispatchQueue.main.async(execute:{

print(“主線程更新 ui \(Thread.current())”)

})

}

}

3.在非同步執行任務,擷取結果,通過 block/閉包 回調。 閉包的應用情境和block完全一致

格式定義特點

1.參數 -> 傳回值

2. loadData(completion: (result : [String]) ->())     ->   ()  中(completion: (result : [String]) ->())  參數,後面是傳回值。

3.completion: (result : [String]) ->()  中   (result : [String])  是參數 後面是傳回值

例:func loadData(completion: (result : [String]) ->() ) ->(){

DispatchQueue.global().async{

print(“耗時操作 \(Thread.current())”)

Thread.sleep(forTimeInterval:1.0)

let json = [“頭條”,”八卦”,”天氣”]

DispatchQueue.main.async(execute:{

print(“主線程更新 ui \(Thread.current())”)

//執行閉包

completion(result: json)

})

}

}

調用

loadData{

(result) in 

print(“擷取成功 \(result)”)

}

 

4.尾隨閉包:如果函數的最後一個參數是閉包,函數參數可以提前結束,最後一個參數直接使用{}封裝閉包的代碼(3的例子)

原始的調用方法(按照函數本身編寫的結果)

loadData(

completion:{(result)->() in

print(“擷取成功 \(result)”)

}

嵌套的尾隨閉包是(系統)不會自動提示尾隨閉包,例如2中的例子。當然也可以手動刪除多餘的來再次寫成尾隨閉包的樣式,方便閱讀

func loadData() ->(){

DispatchQueue.global().async{

print(“耗時操作 \(Thread.current())”)

DispatchQueue.main.async{

print(“主線程更新 ui \(Thread.current())”)

}

}

}

 

5.在OC中可以用{} 來區分範圍。但是在swift中是不行的,swift中遇到{}可能會識別為閉包

 

6.swift中的迴圈應用:

1.使用OC的方式

weak var weakSelf = self

loadData{

print(weakSelf?.view)

}

細節1:要使用var修飾 不能使用let 。 因為weak可能在運行時被修改。weak指向的對象一旦被釋放,會自動化佈建為nil ,所有不能為let 

細節2:?(可選解包)通常用於單純發送訊息,沒有計算       !(強行解包) 強行解包必須有值,如果沒有會造成崩潰,通常用於計算

 

2.Swift推薦方法

loadData{

[weak self] in

print(self?.view)

}

[weak self] 表示閉包中所有的self都是若引用,注意解包

 

3.Swift的一個特殊方法(不建議使用)

loadData{

[unowned self] in

print(self?.view)

}

[unowned self] 表示閉包中所有的都是 assign的,不會強引用。但是對象釋放指標地址不會變化,如果對象被釋放,繼續調用就會造成野指標的問題

 

7. [weak self ]是閉包整self的弱引用,如果self被釋放,會自動化佈建為nil,與OC中的 __weak等效

[unowned self] 是閉包中的self 的assign的 ,如果self被釋放,指標地址保持不變,會出現野指標的錯誤,與OC中的 __unsafe_unretained 等效

  

//demo:https://github.com/fushengit/Learn-Swift 

 

Swift學習(2函數閉包)

相關文章

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.