2010-03-06 13 views
37

tôi đã googled và đến để biết rằng làm thế nào để sử dụng các đối số biến. nhưng tôi muốn chuyển đối số biến của tôi sang phương thức khác. tôi bị lỗi. làm thế nào để làm điều đó ?cách chuyển đối số biến sang phương thức khác?

-(void) aMethod:(NSString *) a, ... { 
    [self anotherMethod:a]; 
    // i m doing this but getting error. how to pass complete vararg to anotherMethod 
} 

Trả lời

49

AFAIK ObjectiveC (giống như C và C++) không cung cấp cho bạn cú pháp cho phép bạn trực tiếp nghĩ gì.

Cách giải quyết thông thường là tạo hai phiên bản của hàm. Một trong đó có thể được gọi trực tiếp bằng cách sử dụng ... và một số khác được gọi bởi các hàm khác chuyển các tham số dưới dạng một va_list.

 
.. 
[obj aMethod:@"test this %d parameter", 1337); 
[obj anotherMethod:@"test that %d parameter", 666); 
.. 

-(void) aMethod:(NSString *)a, ... 
{ 
    va_list ap; 
    va_start(ap, a); 

    [self anotherMethod:a withParameters:ap]; 

    va_end(ap); 
} 

-(void) anotherMethod:(NSString *)a, ... 
{ 
    va_list ap; 
    va_start(ap, a); 

    [self anotherMethod:a withParameters:ap]; 

    va_end(ap); 
} 

-(void) anotherMethod:(NSString *)a withParameters:(va_list)valist 
{ 
    NSLog([[[NSString alloc] initWithFormat:a arguments:valist] autorelease]); 
} 
+1

Có bộ nhớ gọn gàng trong -anotherMethod: withParameters: Bạn cần phải thêm tự động trả tiền cho [[NSString alloc] init] –

+0

true and corrected @Bill – Till

+0

Tuyệt vời! Tôi muốn vượt qua một danh sách các biến đối số để predicateWithFormat: và sau khi bạn đề xuất điều này, tôi nhận ra Apple đã thực sự cung cấp một biến vị ngữWithFormat: arguments: tương đương mà tôi đã không nhận thấy trước đó. – ArtOfWarfare

20

Bạn không thể chuyển trực tiếp đối số variadic. Nhưng một số phương pháp trong số này cung cấp giải pháp thay thế để bạn có thể vượt qua đối số va_list, ví dụ:

#include <stdarg.h> 

-(void)printFormat:(NSString*)format, ... { 
    // Won't work: 
    // NSString* str = [NSString stringWithFormat:format]; 

    va_list vl; 
    va_start(vl, format); 
    NSString* str = [[[NSString alloc] initWithFormat:format arguments:vl] autorelease]; 
    va_end(vl); 

    printf("%s", [str UTF8String]); 
} 
1

Bạn đã xem xét thiết lập đối số của mình trong mảng hoặc từ điển và mã hóa có điều kiện không?

-(void) aMethodWithArguments:(NSArray *)arguments { 
    for (id *object in arguments) { 
     if ([object isKindOfClass:fooClass]) { 
      //handler for objects that are foo 
      [self anotherMethod:object]; 
     } 
     if ([object isKindOfClass:barClass]) { 
      //and so on... 
      [self yetAnotherMethod:object]; 
     } 
    } 
} 
0

Tôi nghĩ bạn có thể sử dụng macro để đạt được điều tương tự. Hãy nói rằng bạn muốn vượt qua đối số biến aMethod của khác

-(void) aMethod:(NSString *) a, ... { 
} 

Bạn có thể xác định một 'phương pháp' của bạn sử dụng vĩ mô mặc dù nó không phải là một phương pháp thực tế:

#define anotherMethod(_a_,...) [self aMethod:_a_,##__VA_ARGS__] 

Đây là giải pháp của tôi.