![](https://img.haomeiwen.com/i6274268/80ed3a69dab24799.jpeg)
1、声明一个block
带参数
typedef void(^nameBlock)(int one,int two);
不带参数
typedef void(^nameBlock)(void);
2、创建一个(property)block参数(block 使用copy修饰符)
typedef void(^nameBlock)(int one,int two);
@property (nonatomic,copy) nameBlock name;
或
@property (nonatomic,copy) void(^nameBlock)(int one,int two);
3、创建一个以block为参数的方法(以自定义弹出框为例)
- (void)createAlertVCWithTitle:(NSString *)title andMessage:(NSString *)message andDefultActionTitle:(NSString *)defultActionTitle andDefultAciton:(void(^)(UIAlertAction *action))defultAction andCancelActionTitle:(NSString *)cancelActionTitle andCancelAction:(void(^)(UIAlertAction *action))cancelAction {
UIAlertController *alertVC = [UIAlertController alertControllerWithTitle:title message:message preferredStyle:UIAlertControllerStyleAlert];
UIAlertAction *actionOne = [UIAlertAction actionWithTitle:defultActionTitle style:UIAlertActionStyleDefault handler:defultAction];
UIAlertAction *actionTwo = [UIAlertAction actionWithTitle:defultActionTitle style:UIAlertActionStyleDefault handler:cancelAction];
[alertVC addAction:actionOne];
[alertVC addAction:actionTwo];
[self.navigationController presentViewController:alertVC animated:YES completion:nil];
}
4、使用block传递button的点击事件
例如自定义CustomView继承与UIView,并添加UIButton
.h
@interface CustomView : UIView
@property (nonatomic,copy) buttonBlock btnBlock;
- (void)createBlockMethod:(buttonBlock)block;
@end
.m
- (instancetype)initWithFrame:(CGRect)frame
{
self = [super initWithFrame:frame];
if (self) {
self.backgroundColor = [UIColor yellowColor];
for (int i = 0; i<3; i++) {
UIButton *btn = [UIButton buttonWithType:UIButtonTypeCustom];
btn.tag = 10+I;
btn.backgroundColor = [UIColor orangeColor];
btn.frame = CGRectMake(10, 10+(60)*i, self.bounds.size.width-20, 50);
[btn setTitle:[NSString stringWithFormat:@"第%d行",i] forState:normal];
[self addSubview:btn];
[btn addTarget:self action:@selector(btnClick:) forControlEvents:UIControlEventTouchUpInside];
}
}
return self;
}
- (void)createBlockMethod:(buttonBlock)block {
self.btnBlock = block;
}
- (void)btnClick:(UIButton *)sender {
self.btnBlock(sender);
}
在ViewController.m里实例化CustiomView
#import "ViewController.h"
#import "CustomView.h"
@implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
CustomView *customView = [[CustomView alloc]initWithFrame:CGRectMake(150, 300, 100, 200)];
[customView createBlockMethod:^(UIButton *sender) {
NSLog(@"这是啥---->%ld",sender.tag);
}];
[self.view addSubview:customView];
}
@end
注意:如果在block里要修改局部变量需要在使用__block修饰该变量 (全局变量则不需要)例如:
- (void)viewDidLoad {
[super viewDidLoad];
int __block a = 10;
self.block = ^(NSString *str) {
a = 20;
};
}
避免block的循环引用,如果A持有B,B中持有A则会造成循环引用(A<->B)引起内存泄漏,例如(当前类持有一个叫block的属性,而block里又持有当前类的属性):
![](https://img.haomeiwen.com/i6274268/04f1a93bf06bc504.jpeg)
这时候需要对self进行弱引用(即使用__weak修饰self,形成弱引用)。如果name属性并不是当前self的属性,则不会引起循环引用,主要是告诉大家,不用见到block块就使用弱引用。
![](https://img.haomeiwen.com/i6274268/7996203ab23b5d5f.jpeg)
既然说到了__weak的使用,那就在说说__weak和__strong的区别
__weak typeof(self) weakSelf = self; //我们根据typeof()括号里面的变量,自动识别变量类型并返回该类型。
self.block = ^(NSString *str) {
__strong __typeof(self) strongSelf = weakSelf;
strongSelf.name = @"测试";
strongSelf.name = @"测试";
strongSelf.name = @"测试";
};
__strong 确保在 Block 内,strongSelf 不会被释放。
总结
(1) 在 Block 内如果需要访问 self 的方法、变量,建议使用 weakSelf。
(2) 如果在 Block 内需要多次 访问 self,则需要使用 strongSelf。
网友评论