2012-03-30 2 views
2

개체를 만든 후에 개체 메서드를 사용하고 싶습니다.목표 C : 생성 후 swizzle 개체 메서드

예 :

@interface MyObj: NSObject 
-(NSString*) foo; 
-(NSString*) bar; 
@end 

@implementation MyObj 
-(NSString*) foo {return @"foo";} 
-(NSString*) bar {return @"bar";} 
@end 

void Swizzle(object, SEL source, SEL, dest); 

...

MyObj* obj = [[[MyObj alloc] init] autorelease]; 

NSLog(@"%@", [obj foo]); 
Swizzle(obj, @selector(foo), @selector(bar)); 
NSLog(@"%@", [obj foo]); 

출력 : 객체가 생성되기 전에 내가 스위 즐링의 examples을 많이 살펴 보았다

foo 
bar 

. 그러나 당신이 볼 수 있듯이 나는 객체가 생성 된 후에 휙휙 놀고 싶다.

NSThread와 같이 출시 할 개체를 추적하고자하기 때문입니다. NSObject dealloc은 너무 과장되어 보일 수 있습니다. 차라리 내가 추적하려고하는 대상 만 뒤집어 쓰고 싶습니다.

+0

[개체가 스레드로부터 안전한 모든 메시지를받을 수있는 방법은 무엇입니까?] (http://stackoverflow.com/questions/8763028/how-can-i-make-every-message-an-object- 수신 스레드 안전). 나는 그것이있는 것처럼 보이지 않지만 답을 보아라. 그것이 필요할 때, 쉽게 풀려 난다. –

+0

"악기 만 사용하십시오." – bbum

답변

0

해결 방법은 objc_setAssociatedObject (thread, key, object, OBJC_ASSOCIATION_RETAIN_NONATOMIC)를 사용하는 것입니다.

그런 식으로 스레드가 릴리스되었을 때이를 감지하고 필요한 정리 작업을 수행 할 수있었습니다.

+0

@ughoavgfhw가 아래에 제안한 내용이 아닙니까? – sergio

0

개체는 특정 클래스에만 적용 할 수 없습니다. 또한 셀렉터에 대한 구현이 캐시되며, 캐시가 자동으로 지워지지 않을 수도 있습니다. 이는 새 메소드가 사용되지 않는다는 것을 의미합니다.

트래킹하려는 클래스에 dealloc을 오버라이드 (또는 swizzling)하고, 추적 코드 수행 여부를 결정하기 위해 속성을 사용하는 것이 좋습니다. 당신이 프레임 워크 클래스를 추적하는 경우

@property (nonatomic) BOOL shouldTrackDealloc; 

@synthesize shouldTrackDealloc; 
- (void)dealloc { 
    if(self.shouldTrackDealloc) { 
     NSLog(@"dealloc of %@",self); 
    } 
    ... 
} 

, 당신은 인스턴스 변수가 올바른 클래스에 없을 것이기 때문에, @synthesize을 사용할 수 없습니다,하지만 당신은 대신 associated references를 사용할 수 있습니다.

2

이것은 솔직히 인스 트루먼 트를 사용하는 것을 피하려고 시도한 것처럼 보입니다. 그렇다면 정답은 "악기 만 사용하십시오"입니다.

하지만 사실 질문에 대답하기 위해 : 당신은 개별 개체로 이것을 할 수 없습니다. 메소드 - 심지어 인스턴스 메소드 -는 객체별로가 아니라 클래스별로 정의됩니다. 개체별로 메서드를 재정의하는 유일한 방법은 관심있는 메서드를 재정의하고 하위 클래스의 조회 테이블을 사용하도록 개체를 isa-swizzle하는 개체 클래스의 하위 클래스를 동적으로 만드는 것입니다. (이것은 기본적으로 KVO가 마술 신고를하는 방식입니다.) 다시 말하지만, 이것은 약간의 해킹이며, 일반적으로 가치가있는 것보다 훨씬 더 많은 문제입니다. 그러기 전에, 나는 정말로 두 번 (또는 세 번) 이것이 정말로 필요한지에 관해서. 거의 모든 유스 케이스가 나오기 때문에 런타임 부두와 관련없는 동일한 목표를 달성 할 수있는 더 깨끗한 방법이 있습니다.

+0

악기를 사용하려고하지 않습니다. 특정 개체의 삭제를 추적하여 정리를 수행 할 수 있습니다. 하위 클래스에 종속되지 않는 기능을 만들려고하기 때문에 객체 클래스를 하위 클래스로 만들고 싶지 않습니다. 예 : NSThread가 만들어지고 액세스 할 수있는 새 객체를 제공하려고합니다.스레드가 죽으면이 개체를 제거하고 싶습니다. 이 클래스의 사용자는 객체가 제거되어야 할 때를 인식하므로 스레드 객체를 조정할 필요가 없습니다. – Peter

+0

@PeterGulyas :이 경우,이 리소스의 생성과 파기를 처리하는 NSThread 하위 클래스가 필요한 것 같습니다. – Chuck

+0

나는 dealloc뿐만 아니라 어떤 객체의 어떤 메소드의 실행을 추적하는 기능을 원합니다. layoutSubviews가 하위 클래스없이 호출 될 때 알면 좋을 것입니다. 예 서브 클래 싱은 간단한 해결책이지만, 나는 더러운 것을 원한다! – Peter