in iPhone

[iPhone] 객체 간 인터페이스 (NSMethodSignature & NSInvocation)

NSMethodSignature & NSInvocation

Cocoa 프로그래밍에서는 위 두개의 클래스를 소개한다.
이는 SDK 2.0이상 사용이 가능하며 iOS 개발에도 유용하게 사용할 수 있다.

메시지 포워딩 또는 n개 이상의 Argument를 전달할 때 사용 할 수 있으며,

실제로 두 클래스는 NSObject클래스에 정의 되어 오버라이딩하여 사용한다.

아래는 예제 코드이다.

[sourcecode language=”objc”]
//
// main.c
// MessageForwarding
//
// Created by hojun baek on 11. 4. 6..
// Copyright 2011 __MyCompanyName__. All rights reserved.
//

#import <Foundation/NSString.h>
#import <Foundation/NSMethodSignature.h>
#import <Foundation/NSInvocation.h>
#import <Foundation/NSAutoreleasePool.h>
#import <stdio.h>
#import <stdlib.h>

@interface EZTest : NSObject{
NSString *str;
}
@end

@implementation EZTest
– (id)initWithString:(NSString *)theStr {
self = [super init];
if (self) {
str = [theStr retain];
}
return self;
}

– (NSMethodSignature *)methodSignatureForSelector:(SEL)aSelector{
if ([super respondsToSelector:aSelector]) {
return [super methodSignatureForSelector:aSelector];
} else {
return [str methodSignatureForSelector:aSelector];
}
}

– (BOOL)respondsToSelector:(SEL)aSelector{
if([super respondsToSelector:aSelector])
return YES;
if([self methodForSelector:aSelector] != (IMP)NULL)
return YES;
if ([str methodForSelector:aSelector]) {
return YES;
}
return NO;
}

– (void)forwardInvocation:(NSInvocation *)anInvocation{
SEL sel = [anInvocation selector];
if ([super respondsToSelector:sel]) {
[super forwardInvocation:anInvocation];
} else {
[anInvocation invokeWithTarget:str];
}
}

// send message with argument.
– (void)print {
SEL selector = @selector(sendWithMsg1:msg2:msg3:);
NSMethodSignature *signature = [[self class] instanceMethodSignatureForSelector:selector];

NSInvocation * invocation = [NSInvocation invocationWithMethodSignature:signature];
[invocation setTarget:self];
[invocation setSelector:selector];

NSString *msg1 = @"welcome ";
NSString *msg2 = @"to ";
NSString *msg3 = @"easy cocoa";

[invocation setArgument:&msg1 atIndex:2];
[invocation setArgument:&msg2 atIndex:3];
[invocation setArgument:&msg3 atIndex:4];
[invocation retainArguments];
[invocation invoke];

}

– (void)sendWithMsg1:(NSString *)msg1 msg2:(NSString *)msg2 msg3:(NSString *)msg3 {
NSLog(@"%@%@%@", msg1, msg2, msg3);
}
@end

int main (int argc, const char * argv[]) {
id test;
id pool = [[NSAutoreleasePool alloc] init];
test = [[EZTest alloc] initWithString:@"hello "];
NSLog(@"%@",[test stringByAppendingFormat:@"world"]);

[test print];
[test release];
[pool release];
return 0;
}
[/sourcecode]

Write a Comment

Comment