block簡介
block是一種基本的數(shù)據(jù)類型,用于存儲代碼塊,在需要的時候調(diào)用,與函數(shù)的區(qū)別是函數(shù)保存的代碼,一旦調(diào)用立即執(zhí)行,block可以在需要時候執(zhí)行.
形式如下:
返回值 (^block名稱)(參數(shù)列表) = ^(參數(shù)列表) {
代碼塊
}
通過返回值和參數(shù)的組合有四種形式:
有參數(shù)有返回值的block
無參數(shù)有返回值的block
沒有返回值有參數(shù)的block
沒有返回值沒有參數(shù)的block
block的typedef使用
和其他的其別名類似,只是block的類型是: ?返回值 (^)()
如下:
DemoBlock就是返回值是int 有兩個參數(shù)為int類型的block, 返回值和參數(shù)是這種類型都是DemoBlock.
block的使用
block作為方法的參數(shù)
block作為作為類的屬性
block作為屬性應(yīng)該用copy修飾
1.當(dāng)用weak序苏、assign修飾block屬性時呻顽,block訪問外部變量捺典,此時block的類型是棧block. 保存在棧中的block, 當(dāng)block所在函數(shù)\\方法返回\\結(jié)束, 該block就會被銷毀. 在其他方法內(nèi)部調(diào)用訪問該block, 就會引發(fā)野指針錯誤.
2.當(dāng)用copy时鸵、strong修飾block屬性時, block訪問外部變量, 此時block的類型是堆block. 保存在堆中的block, 當(dāng)引用計數(shù)器為0時被銷毀, 該類型block是由棧類型的block從棧中復(fù)制到堆中形成的, 因此可以在其他方法內(nèi)部調(diào)用該block. 在ARC下胀蛮,strong和copy都可以用來修飾block, 但是建議修飾block屬性使用copy.
這兩種是block的常用使用方式,具體在下面代碼中展示.
block傳值與回調(diào)
block在傳值和回調(diào)方面和代理的作用相同,block使用簡潔方便一點,
在網(wǎng)絡(luò)異步回調(diào)時一般都使用block回調(diào),下面使用兩個小案例進行演示.
第一個: 反向傳值,將一個參數(shù)從一個控制器傳到另一個控制器.
將輸入的文本從B控制器點擊點擊按鈕傳到A控制器
代碼實現(xiàn)部分
B控制器添加一個block屬性
添加按鈕,在點擊的時候?qū)⑽谋究騼?nèi)的字符串傳到A控制器并返回到A控制器
接收傳過來的數(shù)據(jù)并顯示到label上
第二個:block回調(diào),通過一個自定義工具類回調(diào)返回數(shù)據(jù)
點擊存儲文本框中內(nèi)容,保存到沙盒,
再點擊通過自定義工具類取出沙盒內(nèi)容,回調(diào)返回數(shù)據(jù)
控制器回調(diào)方法
自定義工具類類方法
block傳值與回調(diào)Demo的源碼
源碼地址 https://git.oschina.net/weidream/MyCode.git
block的使用注意事項
1.block內(nèi)部不能直接修改局部變量
block內(nèi)部可以訪問外部的變量, 默認(rèn)是將其拷貝到其數(shù)據(jù)結(jié)構(gòu)中來實現(xiàn)訪問的, 屬性是只讀的. ?block內(nèi)部不能修改外面的局部變量.
如果要修改需要對要修改的局部變量用__block 修飾, 這樣局部變量就可以在block內(nèi)部修改了倘零,block是復(fù)制其引用地址來實現(xiàn)訪問的
2.當(dāng)block里面的出現(xiàn)self,造成的循環(huán)引用
循環(huán)引用就是當(dāng)self 擁有一個block的時候, 在block中又調(diào)用self的方法. 形成了你中有我, 我中有你, 造成誰都無法將誰釋放, 從而發(fā)生內(nèi)存泄漏.
解決方法:
__weak typeof (self) weakSelf = self;
定義一個weakSelf變量并加上__weak修飾符, 在Block代碼塊中, 所有需要self的地方都用weakSelf來替代铛绰。這樣就不會增加引用計數(shù), 所以Block持有self對象也就不會造成循環(huán)引用舞吭,從而造成內(nèi)存泄漏.