码迷,mamicode.com
首页 > 其他好文 > 详细

block注意事项

时间:2015-05-06 01:14:19      阅读:176      评论:0      收藏:0      [点我收藏+]

标签:

1.block的声明和注意事项

#import "ZYViewController.h"

@interface ZYViewController ()

@end

/*用typedef可以声明一种类型的block*/

//block前加上typedef, 那么就不是一个block指针(变量),而是一种block类型
//给int (^) (int a, int b) 这种block类型 声明了一个别名,叫做Block5
typedef int (^Block5) (int a, int b);

//Block6就是无参无返回的block的类型
typedef void (^Block6) (void);

@implementation ZYViewController


- (void)viewDidLoad
{
    [super viewDidLoad];
            
    //block
    //原理:block也是指针,指向的不是对象的内存地址,而是一段代码块的地址
    
    //void/*返回类型*/ (^/*代表是指针类型*/ block1/*变量名*/) (void/*参数*/) = NULL/*初值为空*/;
    
    //无参无返回的block,如果无参,参数可以写void,也可以不写
    void (^block1) (void) = NULL;
    //block1的类型  void (^) (void) 无参无返回的类型
    //给block赋值,无参的block赋值,在=后可以写成^(void)、^()、^,如果不是无参的,那么必须把参数类型和形参名写完整
    block1 = ^(void) {
        NSLog(@"hello world");
    };
    //执行block
    block1();
    
    
    //有参无返回
    //void (^block2) (int)中的(int)只是声明该block参数的个数,以及每个参数的类型,在声明的时候可以不写形式参数,但是在实现的时候必须写形式参数,而且实现时的形式参数名可以和声明时不同
    void (^block2) (int n) = ^(int n) {
        NSLog(@"------>%d", n);
    };
    block2(222);
    
    //多参无返回,每个参数之间用","分割,在执行的时候需要注意参数的顺序
    void (^block3) (int age, NSString *name) = ^ (int age, NSString *name) {
        NSLog(@"%@今年 %d岁", name, age);
    };
    block3(1000, @"龟小妹");
    
    //有参有返回
    int (^block4) (int a, int b) = ^(int a, int b) {
        return a + b;
    };
    int sum = block4(1, 7);
    NSLog(@"--------->%d", sum);
    
    Block5 block5 = NULL;
    block5 = ^(int a, int b) {
        return a + b;
    };
    int sum1 = block5(100, 1);
    NSLog(@"--------->%d", sum1);
    
    
    //基本数据类型
    //1.对于局部的不添加“__block”的基本数据类型,block用到的是对变量的值的拷贝,在block中对变量赋值没用意义
    //2.对于局部的添加“__block”的基本数据类型,block中不会对变量的值进行拷贝,可以在block中对变量进行赋值
    //3.对于全局基本数据类型的变量,除了作用范围不同外,其他的同添加“__block”的局部变量
    __block int num = 0;
    NSLog(@"地址1----->%p", &num);
    void (^block6) (void) = ^(void) {
        NSLog(@"1**************  %d", num);
        NSLog(@"地址2----->%p", &num);
        num = 20;
    };
    num = 10;
    NSLog(@"2**************===  %d", num);
    NSLog(@"地址3----->%p", &num);
    block6();
    NSLog(@"3**************===  %d", num);
    
    
    //指针类型
    //1.对于不添加“__block”的局部指针,block中用到的是指针的拷贝,可以用此拷贝的指针去更改对象的属性,但是不能直接更改对象
    //2.对于添加“__block”的局部指针,block中不会对指针进行拷贝,可以更改对象
    //3.对于全局的指针,除了作用范围外,其他同添加“__block”的局部指针
    __block ZYTest *test = [[ZYTest alloc] init];
    //NSLog(@"1----->%@---->%p", test, &test);
    //NSLog(@"1----->%@", test.date);
    void (^block7) (void) = ^(void) {
        NSLog(@"2----->%@---->%p", test, &test);
        test = [[ZYTest alloc] init];
        test.date = [NSDate date];
        NSLog(@"2----->%@", test.date);
    };
    
    //NSLog(@"3----->%@---->%p", test, &test);
    NSLog(@"3----->%@", test.date);
    block7();
    NSLog(@"4----->%@---->%p", test, &test);
    NSLog(@"5----->%@", test.date);
    
        
}

2.block的内存问题

 //1.block变量的copy,不会增加全局的或者是添加“__block”的局部指针的引用计数
    //2.block变量的copy,会把不添加“__block”的局部指针指向的对象retain一次
    NSDate *date = [NSDate date];    
    void (^tempBlock) (int n) = ^(int n) {
        //NSLog(@"专业测试语句,请勿模仿-->%d", n);
        NSLog(@"2---->%d", date.retainCount);
    };
    block1 = [tempBlock copy];
    //block1(50);
    //NSLog(@"3---->%d", date.retainCount);
    
    
    self.block2 = ^(void) {
        NSLog(@"======专业测试语句,请勿模仿");
    };
    
    
    __block ZYViewController *tempSelf = self;
    NSLog(@"1----->self.retainCount=%d", self.retainCount);
    void (^block3) (void) = ^(void) {
        [tempSelf test];
        NSLog(@"2----->self.retainCount=%d", tempSelf.retainCount);
    };
    self.block2 = block3;
    _block2();
    NSLog(@"3----->self.retainCount=%d", self.retainCount);



#import <UIKit/UIKit.h>
#import "ZYSecViewController.h"

@interface ZYViewController : UIViewController
{
    //声明一个全局的block,因为block声明在栈上,所以对于全局的block赋值要添加一个copy,把其拷贝到堆上,而且在dealloc中要添加该block的释放语句
    void (^block1) (int n);
    
    NSDate *now;
    
}

//采用这种方式也可以声明一个全局的block,自动生成的block变量带一个"_",描述的时候要用copy,如果在其他类中需要使用block作为一个属性,则必须要@property描述
@property(nonatomic, copy)void (^block2) (void);


 

block注意事项

标签:

原文地址:http://www.cnblogs.com/keyan1102/p/4480634.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!