Objective C中的块语法是出了名的不协调。将块作为参数传递与将块声明为ivars不同,后者与对块进行类型定义不同。
是否有一个完整的块声明语法列表,我可以随时保存以供快速参考?
Objective C中的块语法是出了名的不协调。将块作为参数传递与将块声明为ivars不同,后者与对块进行类型定义不同。
是否有一个完整的块声明语法列表,我可以随时保存以供快速参考?
Xcode 4代码段库包含块类型defs和内联块作为变量的模板。它们也可以通过自动补全(typedefblock和inlineblock)来实现。
对于作为方法参数的块,我建议声明一个类型定义,然后简单地使用它。它使代码更容易阅读。
类型:
typedef void (^block)(NSString *arg);
内联:
void (^block)(NSString *) = ^(NSString *param) {
// do something....
};
方法:
- (void)method:(void (^)(NSString *param))handler
块声明语法列表
在,让
Return_type是对象/原语/等等的类型。你想返回(通常是无效的) blockName是你正在创建的块的变量名 Var_type类型为object/primitive/etc。您想要作为参数传递(不带参数时留空) varName是给定参数的变量名
请记住,您可以创建任意多的参数。
块作为变量
可能是最常见的of声明。
return_type (^blockName)(var_type) = ^return_type (var_type varName)
{
// ...
};
块作为属性
很像将块声明为变量,只是略有不同。
@property (copy) return_type (^blockName) (var_type);
块作为参数
注意这不同于“Blocks as Arguments”;在本例中,您声明了一个需要块参数的方法。
- (void)yourMethod:(return_type (^)(var_type))blockName;
块作为参数
注意,这与“Blocks as Parameters”不同;在这个实例中,您正在调用一个方法,该方法需要一个带有匿名块的块参数。如果已经声明了块变量,那么将变量名作为参数传递就足够了。
[someObject doSomethingWithBlock: ^return_type (var_type varName)
{
//...
}];
匿名块
这在功能上是一个匿名块,但是将块分配给变量的语法只是简单地将变量设置为匿名块。
^return_type (var_type varName)
{
//...
};
typedef块
这允许您设置一个短名称,可以在声明块期间像引用任何其他类名一样引用它。
typedef return_type (^blockName)(var_type);
为了以后使用blockName代替标准块声明语法,只需替换即可。
内联块
这可以说是对区块的一种不太有用的利用,但仍然有它的一席之地。内联块是在实例化后立即调用的匿名块。
^return_type (var_type varName)
{
//...
}(var);
内联块主要用于范围偏移,大致相当于简单的用大括号分隔的代码块。
{
//...
}
递归的块
这允许您从自身调用一个块,创建一个可以在回调和GCD调用期间使用的循环。这种实例化方法在ARC中没有保留周期。
__block return_type (^blockName)(var_type) = [^return_type (var_type varName)
{
if (returnCondition)
{
blockName = nil;
return;
}
// ...
} copy];
blockName(varValue);
返回块
方法可以返回一个块,
- (return_type(^)(var_type))methodName
{
// ...
}
就像一个函数一样,如果有点奇怪的话。
return_type (^FunctionName())(var_type)
{
// ...
}
附件
如果我遗漏了什么,请在评论中告诉我,我会研究/添加它们。
哦,在斯威夫特…
blockName = (varName: var_type) -> (return_type)
这就像是一种语言特性。
如果你需要回到Xcode 4.2中,你也可以@synthesize一个声明为属性的block,就像你使用非block属性一样。不要让块语法打倒你。
如果你的block属性是:
@property (copy) return_type (^blockName) (var_type);
然后你的@synthesize是这样的:
@property blockName;
欢呼。
我个人喜欢使用这个网站(http://fuckingblocksyntax.com)。这个名字比块语法本身更容易记住:
http://fuckingblocksyntax.com
如果你不能加载含有脏话的url,你可以使用这个镜像:http://goshdarnblocksyntax.com
我为一个类写了一个completionBlock,它将返回一个骰子被摇后的值:
Define typedef with returnType (.h above @interface declaration) typedef void (^CompleteDiceRolling)(NSInteger diceValue); Define a @property for the block (.h) @property (copy, nonatomic) CompleteDiceRolling completeDiceRolling; Define a method with finishBlock (.h) - (void)getDiceValueAfterSpin:(void (^)(NSInteger diceValue))finishBlock; Insert previous defined method in .m file and commit finishBlock to @property defined before - (void)getDiceValueAfterSpin:(void (^)(NSInteger diceValue))finishBlock{ self.completeDiceRolling = finishBlock; } To trigger completionBlock pass predefined variableType to it (Don't forget to check whether the completionBlock exists) if( self.completeDiceRolling ){ self.completeDiceRolling(self.dieValue); }
typedef void (^OkBtnBlock)(id data);
typedef void (^CancelBtnBlock)();
@property (nonatomic, strong) OkBtnBlock okBtnBlock;
@property (nonatomic, strong) CancelBtnBlock cancelBtnBlock;
+ (void)foo:(OkBtnBlock)okBtn andCancel:(CancelBtnBlock)btnCancel;