blocks(闭包)学习笔记

来源:互联网 发布:海尔三网电视网络升级 编辑:程序博客网 时间:2024/05/16 17:10


1、block 可以访问相同作用域范围内定义的变量

2、Blocks 的最大一个特色就是可以修改相同作用域的变量。你可以使用__block 存 储类型修饰符来给出信号要修改一个变量。
在函数级别是__block变量。这些在block里面是可变的(和封闭范围),并任何引用 block 的都被保存一份副本到堆里面。 

3、一个 block 的大小是无法在编译的时候计算的。

4、默认情况下当你在 block 里面引用一个 Objective-C 对象的时 候,该对象会被 retain。但是被__block 存储类型修饰符标记的对象变量不会被 retain.

如果你在实现方法的时候使用了 block,对象的内存管理规则更微妙:
如果你通过引用来访问一个实例变量,self 会被 retain。
如果你通过值来访问一个实例变量,那么变量会被 retain。

下面举例说明两个方式的不同:

dispatch_async(queue, ^{
// instanceVariable is used by reference, self is retained
doSomethingWithObject(instanceVariable);

});

id localVariable = instanceVariable;
dispatch_async(queue, ^{

// localVariable is used by value, localVariable is retained (not self)

doSomethingWithObject(localVariable);

});

page15image40928


5、当你拷贝一个基于栈的 block 时,你会获得一个新的 block。但是如果你拷贝一个 基于堆的 block,你只是简单的递增了该 block 的引用数,并把原始的 block 作为函数 或方法的返回值

6、通常,你不需要 copy(或 retain)一个 block.在你希望 block 在它被声明的作用域 被销毁后继续使用的话,你子需要做一份拷贝。拷贝会把 block 移到堆里面(block默认是在栈中)。

你可以使用 C 函数来 copy 和 release 一个 block:
Block_copy();
Block_release();

如果你使用 Objective-C,你可以给一个 block 发送 copy、retain 和 release(或 autorelease)消息。 

7、 调试
你可以在 blocks 里面设置断点并单步调试。你可以在一个 GDB 的对话里面使用invoke-block 来调用一个 block。如下面的例子所示:

$ invoke-block myBlock 10 20
如果你想传递一个 C 字符串,你必须用引号括这它。例如,为了传递 this string 给 doSomethingWithString 的 block,你可以类似下面这样写:

$ invoke-block doSomethingWithString "\"this string\""

page21image39480

 

原创粉丝点击