In Objective C what is the equivalent of passing a function pointer in C?
@implementation ThisObject
-(void)start {
开发者_运维知识库 SomeOtherObject *someOtherObject = [SomeOtherObject alloc];
[someOtherObject doSomethingAndCallThisFunctionWhenUrDone:myCallBackFunction :self];
}
-(void)myCallBackFunction {
// :)
}
Basically, how can I make this work?
There are four ways to make a callback:
Function Pointer You can do a function pointer if you really want, but it's not recommended. It's done the same way you would do it in C. The problem is you can't use a function pointer to an Objective-C method. It looks something like this:
void callback(/* Some args */) { // Some callback. } - (void)doSomethingAndCallThisFunctionWhenDone:(void(*)(/* Some args */))func { // Do something. if (func) func(/* Some args */); } - (void)start { [self doSomethingAndCallThisFunctionWhenDone:&callback]; }
Selectors You can use -performSelector:. It looks like this:
- (void)doSomethingAndCallTarget:(id)target withSelector:(SEL)sel { // Do something. [target performSelector:sel]; } - (void)start { SomeOtherObject * someOtherObject = [[SomeOtherObject alloc] init]; [self doSomethingAndCallTarget:someOtherObject withSelector:@selector(MyCallback)]; }
Delegates Use a delegate. This is similar to UITableViewDelegate/UITableViewDataSource. See the Apple docs here. You might do it like this:
- (void)doSomethingDelegate:(id<MyCallbackObject>)delegate { [delegate retain]; // Do something. [delegate performMyCallback]; // -performMyCallback must be declared in the MyCallbackObject protocol and implemented by SomeOtherObject. [delegate release]; } - (void)start { id<MyCallbackObject> someOtherObject = [[SomeOtherObject alloc] init]; [self doSomethingDelegate:someOtherObject]; [someOtherObject release]; }
Blocks The preferred way for callbacks is to use blocks. They are only available for iOS 4.0+ or Mac OS X 10.6+. It looks something like this:
- (void)doSomethingAndCallThisBlockWhenDone:(void(^)(/* Some args */))block { [block copy]; // Do something. if (block) block(/* Some args */); [block release]; } - (void)start { [self doSomethingAndCallThisBlockWhenDone:^void(/* Some args */){ // Return type and arguments may be omitted if you don't have any. // Your callback }]; }
As you can see with the block, it's easier to read and your callback is inline with your code. This is especially nice so you don't have to hunt it down. There are many more benefits of blocks, but I couldn't possibly cover them all here.
One last thing, if you use a block, you will want to use a typedef
so you don't have to type obscure block types like void(^)(/* Some args */)
all the time. The typedef
could look like this:
typdef void(^MyCallback)(/* Some args */);
Then, you can declare your method like this:
- (void)doSomethingAndCallThisBlockWhenDone:(MyCallback)block;
Update:
I have shown more detail of how to implement the different techniques (see above).
Are you talking about this?
-(void)callSomePassedSelector:(SEL)callbackSelector {
[someObjectThatRespondesToThisSelector performSelector:callbackSelector];
}
I assume you want to store it and call it later, but this should give you all the needed information about how to pass and call it. There are other methods to invoke the selector, see more here
im a bit confused about what you talking about but is this it?
[self performSelector:@selector(myCallFunction)];
精彩评论