美文网首页iOS开发
block的捕获值

block的捕获值

作者: 请叫我魔法师 | 来源:发表于2017-07-25 16:11 被阅读37次

    接上回。
    一、上篇提到swift闭包的问题,估计和block同本同源。查了写别人写的关于闭包的,都会提到闭包的一个特点。捕获值。
    解释:闭包可以在其被定义的上下文中捕获常量或变量。即使定义这些常量和变量的原作用域已经不存在,闭包仍然可以在闭包函数体内引用和修改这些值。
    这个怎么理解?有什么用?
    其实就是把B函数把闭包A作为返回值传递出去,在全局中获得了A闭包,但是A闭包可以操作B函数的局部变量,这样就实现了捕获局部变量。swift 的例子也简单,为了省事,这次接着用OC的block说明这个问题。
    PS:OC快淘汰了,赶紧看swift啦啦啦啦。

    上文说到,如果一个函数作为参数或者返回值传到另外一个函数里,那么这个函数就成了block。block如果作为参数传递,就实现了回调的功能,block如果作为返回值返回出来,就实现了捕获值的功能。这就是本文的重点。

    - (void(^)())testFunction3WithParameter:(NSString *)title{
        
        NSLog(@"方法3的实现 -- %@", title);
        __block int index = 0;
        void(^block)() = ^(){
            index = index + 1;
            NSLog(@"block的实现--%d", index);
        };
        return block;
    }
    
    

    定义并实现了一个函数,可以看到返回值比较特殊,是个block,也就是返回了一个函数,不是常见的void或者int等等。
    和回调不同的是,block的定义实现写在了一起,调用依然和实现分开。
    在这个函数内部,我定义了一个int类型,并定义实现了一个block,在实现代码中,我给这个局部变量index每次加1.最后把block返回出去。
    接下来改调用这个函数了:

        void(^myBlock)() = [self testFunction3WithParameter:@"方法3"];
        myBlock();
        myBlock();
        myBlock();
    

    由于这个函数返回值是个函数,所以必须用函数接收,定义了一个函数,叫block,接受了这个方法的返回值。
    前面说到,我把block的定义和实现写在了一起,还没有调用,所以在这里接收到block后,再调用,第一次调用,执行block的大括号里面的代码,打印1,再执行打印2,再执行打印3,这就是捕获值。block捕获到了它所在的函数的局部变量,并在全局中调用,并且这个值保存在内存中,相当于成了要给全局变量,每次操作都保留了最新结果。


    QQ20170725-154008.png

    所以block也有这个捕获值的特点,和闭包一样,虽然还不清楚有啥卵用。

    二、block也是引用类型(说不清了,我也不懂)

    因为函数也是引用类型?这么解释?
    PS:值类型和引用类型
    // 值类型:指的是当一个变量赋值给另外一个变量的时候, 是copy一个副本
    // 两个变量之间互不影响, 也就是说, 另外一个变量的值改变, 不会影响到另外一个变量
    // 也就是传的只是一个值, 不是一个引用(地址)
    int a = 0
    int b = a
    b = 2
    最后打印结果是a = 0, b = 2;b对a没有影响

    // 闭包和函数都是引用类型
    // 引用类型:指的是当引用类型变量赋值给另外一个变量的时候, 其实两个变量指的都是同一个内容
    // 当其中一个变量修改了这个内容, 另外一个变量也会跟着改变

    对于block,代码如下

        void(^myBlock)() = [self testFunction3WithParameter:@"方法3"];
        myBlock();
        myBlock();
        myBlock();
        
        void(^myBlock1)() = myBlock;
        myBlock1();
    
    QQ20170725-161534.png

    再用个相同类型的block=myBlock,最后打印结果是4,说明是同一个对象,所以说block也是引用类型。

    相关文章

      网友评论

        本文标题:block的捕获值

        本文链接:https://www.haomeiwen.com/subject/bygwkxtx.html