【发布时间】:2012-11-22 11:13:59
【问题描述】:
据我所知,这与 SO 上的其他“我可以检查块的类型”帖子不同。
我想知道,给定一个未知签名的块对象,我是否可以在调用之前了解它接受哪些参数?
我有一些与字典中的对象相关联的回调的情况。我希望其中一些回调期望一组不同的参数。这里的例子非常简化,但我认为它明白了重点。
我如何确定一个块是否属于我之前定义的类型?
//MyClass.m
// I start by declare two block types
typedef void (^callbackWithOneParam)(NSString*);
typedef void (^callbackWithTwoParams)(NSString*, NSObject*);
........
// I create a dictionary mapping objects to callback blocks
self.dict = @{
@"name": "Foo",
@"callback": ^(NSString *aString) {
// do stuff with string
}
}, {
@"name": "Bar",
@"callback": ^(NSString *aString, NSObject *anObject) {
// do stuff with string AND object
}
}
.....
// Later, this method is called.
// It looks up the "name" parameter in our dictionary,
// and invokes the associated callback accordingly.
-(void) invokeCallbackForName:(NSString*)name {
// What is the type of the result of this expression?
[self.dict objectForKey: name]
// I want to say: (pseudocode)
thecallback = [self.dict objectForKey: name];
if (thecallback is of type "callbackWithOneParam") {
thecallback(@"some param")
}
else if (thecallback is of type "callbackWithTwoParams") {
thecallback(@"some param", [[NSObject alloc] init]);
}
}
【问题讨论】:
-
我认为你不能。在你的情况下,你可以留下额外的参数 NSObject ,如果你不使用它,就放 nil 。
-
在本例中,最好对字典中的所有块使用一致的签名。然后,每个块中的代码可以独立决定使用或忽略哪些参数。您还必须将
-objectForKey:的返回值转换为您的块签名,然后才能调用该块。您还必须在将每个块添加到字典之前将其复制到堆中。 -
Darren 能否详细说明您的最后两个陈述,谢谢!
-
首先,您的字典语法无效。您的意思可能类似于
@{ @"Foo": ^(...) {...}, @"Bar": ^(...) {...} }。其次,您需要先复制一个块,然后再将其放入字典之类的通用集合中,否则会发生不好的事情。 -
创建一个 NSOperation 的子类。
标签: objective-c ios objective-c-blocks