2011-08-16 9 views
5

Tôi đang cố chuyển một bộ chọn làm tham số và thực thi nó sau này. Nhưng tôi nhận được một lỗi SIGABRT khi tôi cố gắng để gọi bộ chọn với các lỗi kế tiếp trong giao diện điều khiển:Mục tiêu-C: Chuyển bộ chọn làm tham số và sau đó gọi nó là

Chấm dứt ứng dụng do ngoại lệ uncaught 'NSInvalidArgumentException', lý do: '- [HttpRequest OnFinishConn:]: chọn không được công nhận gửi đến dụ 0x7834c80'

HttpRequest.h

#import <Foundation/Foundation.h> 

@interface HttpRequest : NSObject 
{ 
    @private SEL onEndSel; 
    @private NSMutableData* receivedData; 
} 
-(void) StartRequest:(NSString *) url 
      parameters:(NSString*) params 
      onEndSelector:(SEL) selector; 
@end 

HttpRequest.m

#import "HttpRequest.h" 

@implementation HttpRequest 

-(void) StartRequest:(NSString *)url 
      parameters:(NSString*)params 
      onEndSelector:(SEL)selector 
{ 
    receivedData = [[NSMutableData alloc] init]; 
    NSMutableURLRequest *request = 
    [[NSMutableURLRequest alloc] initWithURL:[NSURL URLWithString:url]]; 
    [request setHTTPMethod:@"POST"]; 
    [request setHTTPBody:[params dataUsingEncoding:NSUTF8StringEncoding]]; 
    onEndSel = selector; 
    NSURLConnection* conn = [[NSURLConnection alloc] initWithRequest:request delegate:self]; 


} 
-(void) connectionDidFinishLoading:(NSURLConnection*) connection 
{ 
    //NSLog([[NSString alloc] initWithData:receivedData encoding:NSUTF8StringEncoding]); 
    [self performSelector:onEndSel withObject:[[NSMutableData alloc] initWithData:receivedData]]; 
} 
-(void) connection:(NSURLConnection *)connection didReceiveData:(NSData *)data{ 
    [receivedData appendData:data];  
} 
@end 

AppDelegate.m

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions 
{ 
    //self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]]; 
    // Override point for customization after application launch. 
    //self.window.backgroundColor = [UIColor whiteColor]; 
    HttpRequest* req = [[HttpRequest alloc] init]; 
    SEL mysel = @selector(OnFinishConn:); 
    NSString * url = [[NSString alloc] initWithString:@"http://www.google.es"]; 
    [req StartRequest:url parameters:@"a" onEndSelector:@selector(OnFinishConn:)]; 
    [self.window makeKeyAndVisible]; 

    return YES; 
} 
-(void)OnFinishConn:(NSMutableData *)data 
{ 
    NSLog([[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding]); 
} 

Tôi mới trong mục tiêu c, vì vậy hãy kiên nhẫn.

+0

Mặc dù không trả lời câu hỏi của bạn, nhưng thực tế là bạn đặt câu hỏi này, dẫn tôi khuyên bạn nên thử ASIHttpRequest, thay vì tạo lại bánh xe – Jonathan

Trả lời

6

Đó là vì bạn đang thử sử dụng mẫu target-action nhưng không chuyển mục tiêu. Tôi thực sự khuyên bạn nên tiếp cận đại biểu nhưng đây là một ví dụ về giao diện của bạn sẽ trông như thế nào.

@interface HttpRequest : NSObject 
{ 
    @private 
    id onEndTarget; //<- need to know who to send the message to (do not retain) 
    SEL onEndSel; 
    NSMutableData* receivedData; 
} 

//Accept the target here 
-(void) StartRequest:(NSString *) url 
      parameters:(NSString*) params 
      onEndTarget:(id)target 
      onEndSelector:(SEL) selector; 

//... implementation 

-(void) connectionDidFinishLoading:(NSURLConnection*) connection 
{ 
    [onEndTarget performSelector:onEndSel withObject:[[NSMutableData alloc] initWithData:receivedData]]; 
} 

//... 
//Inside App Delegate 
[req StartRequest:url parameters:@"a" onEndTarget:self onEndSelector:@selector(OnFinishConn:)]; 

Đảm bảo bạn không giữ lại mục tiêu onEndTarget vì có thể tạo chu kỳ lưu giữ. Ngoài ra, hãy xem xét việc tạo mục tiêu cho một thuộc tính để nếu có điều gì đó được thực hiện với kết nối trước khi nó hoàn thành, nó có thể ngừng làm đại biểu.

+0

Cảm ơn tất cả các câu trả lời của bạn. Nó hoạt động tốt với mã của Joe. – Payn3

+0

Vui mừng họ đã giúp đảm bảo đánh dấu một câu hỏi như đã được trả lời sau khi sự cố của bạn được giải quyết và chào mừng bạn đến với StackOverflow !. – Joe

4

Bạn đang gửi bộ chọn đến self, nhưng đó là trong HttpRequest. Bộ chọn bạn đang cố gọi là trong AppDelegate. Vì vậy, bạn đang gửi bộ chọn đến một đối tượng không thực hiện nó. Để khắc phục, bạn nên lưu trữ không chỉ bộ chọn mà là con trỏ tới đối tượng mà bộ chọn sẽ được gửi.

1

Vui lòng đọc tài liệu trên NSInvocation hoặc chuyển một khối làm thông số nếu hệ điều hành đích của bạn hỗ trợ.

+0

Brillliant. Đây sẽ là câu trả lời –