2009-05-31 4 views
51

:@selector를 매개 변수로 전달하는 방법은 무엇입니까? 방법에 대한

[NSThread detachNewThreadSelector:@selector(method:) toTarget:self withObject:(id)SELECTOR]; 

은 어떻게 @selector를 전달합니까? 나는 그것을 (id)에 캐스팅하여 컴파일되도록 시도했지만 런타임에는 크래시된다. 그것은 충돌

+(void)method1:(SEL)selector{ 
[NSThread detachNewThreadSelector:@selector(method2:) toTarget:self withObject:selector]; 
} 

:


더 구체적으로,이 같은 방법이있다. 스레드가 준비되면 새 스레드가 선택기를 호출 할 수 있도록 충돌없이 선택기를 전달하는 방법은 무엇입니까?

답변

67

여기서 문제는 선택기를 메서드 자체에 전달하는 것이 아니라 개체가 예상되는 곳에 선택기를 전달하는 것입니다. 비 객체 값을 객체로 전달하려면 NSValue을 사용할 수 있습니다. 이 경우 NSValue를 받아들이고 적절한 selector를 가져 오는 메소드를 만들어야합니다.

@implementation Thing 
- (void)method:(SEL)selector { 
    // Do something 
} 

- (void)methodWithSelectorValue:(NSValue *)value { 
    SEL selector; 

    // Guard against buffer overflow 
    if (strcmp([value objCType], @encode(SEL)) == 0) { 
     [value getValue:&selector]; 
     [self method:selector]; 
    } 
} 

- (void)otherMethodShownInYourExample { 
    SEL selector = @selector(something); 
    NSValue *selectorAsValue = [NSValue valueWithBytes:&selector objCType:@encode(SEL)]; 
    [NSThread detachNewThreadSelector:@selector(methodWithSelectorValue:) toTarget:self withObject:selectorAsValue]; 
} 
@end 
+0

+50 우수! 이 작업을 수행하는 방법을 결코 기억할 수 없습니다 ... – bentford

+0

새 스레드로 그 비트를해야하는 이유는 무엇입니까? – cstack

+2

@cstack : 질문을 보면, 새로운 스레드를 생성하는 것은 OP가 시도한 것입니다. 그래서 나는 나의 예에서 같은 작업을 사용했다. 그러나이 기법은 새로운 스레드를 생성하는 데 어떤 방식으로도 사용되지 않습니다. – Chuck

0

그냥 전무를 사용합니다.

[NSThread detachNewThreadSelector:@selector(method:) toTarget:self withObject:nil]; 

개체를 선택기로 전달해야하는 경우 다음과 같이 표시됩니다.

여기서는 "setText"메서드에 문자열을 전달하고 있습니다.

NSString *string = @"hello world!"; 
[NSThread detachNewThreadSelector:@selector(setText:) toTarget:self withObject:string]; 


-(void)setText:(NSString *)string { 
    [UITextField setText:string]; 
} 
+0

은 업데이트 된 질문을 참조하십시오. 고맙습니다! – erotsppa

4

사용 NSValue과 같이, : 예를 들면 다음과 같습니다 구현입니다

+(void)method1:(SEL)selector { 
    NSValue *selectorValue = [NSValue value:&selector withObjCType:@encode(SEL)]; 
    [NSThread detachNewThreadSelector:@selector(method2:) 
          toTarget:self 
          withObject:selectorValue]; 
} 

NSValue는 임의의 비 객체 유형의 객체 래퍼위한 것입니다.

+0

"selector ..."앞에 "&"기호가 누락되어 "... value : selector ..."대신 "... value : & selector ..."가됩니다. – Senseful

+0

참. 주의 해 주셔서 감사합니다. 나는 그것을 고쳤다. –

41

NSStringFromSelector()NSSelectorFromString() 기능을 사용하여 선택기와 문자열 개체간에 변환 할 수 있습니다. 그래서 대신 문자열 객체를 전달할 수 있습니다.

메소드를 변경하지 않으려면 NSInvocation을 작성하여 메소드 호출에 대한 호출을 작성한 다음 (비 오브젝트 인수로 호출을 설정할 수 있으므로) 호출 한 다음 호출하십시오 [NSThread detachNewThreadSelector:@selector(invoke) toTarget:myInvocation withObject:nil];

+0

이것은 더 많은 upvotes가 필요합니다. –

+0

이것은 많은 것에 대한 최선의 대답입니다. 더 많은 사람들이이 것을 upvote 할 수 있기를 바랍니다. –

+0

많은 감사, 이것은 내가 필요한 것입니다. – amergin

관련 문제