2011-05-21 49 views
1

我有一個應用程序,使用segmentedControl。第一項是一個「全部」項,其餘的是根據webservice的結果從數組創建的。當選擇「全部」時,我想請求所有請求。NSArray與多個嵌套請求

我怎麼能去這,

NSArray *urls = [NSArray arrayWithObjects:@"http://service/group/1/", 
              @"http://service/group/2/", nil]; 

我想收集從電話到一個集合中的所有結果,並在一個UITableView顯示它時選擇了「全部」項並可能在viewDidLoad中。 對於其它段僅請求中的一個被髮出,並用一個數組回調然後在使用:

-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath { 

我試圖看這個例子,用於從陣列發出請求MultipleDownloads

謝謝,

在我的viewController的方法來啓動多重下載:

- (void)requestChildrenInBackground { 

queue = [[NSOperationQueue alloc] init]; 

//Todo remove hard coded and get from previous request respons 
NSArray *urls = [NSArray arrayWithObjects: @"http://service/1/children", 
       @"http://service/2/children", 
       @"http://service/3/children", nil]; 

NSLog(@"%@", urls);  
for (NSString * url in urls) 
{ 
    GetSchedule *operation = 
    [GetSchedule urlDownloaderWithUrlString:url]; 
    [queue addOperation:operation]; 
} 
} 

這是豪w多重請求得到處理:

#import "GetSchedule.h" 

#import "JSON.h" 
#import "Authentication.h" 
#import "AttendanceReportViewController.h" 

@interface GetSchedule() 

- (void)finish; 

@end 

@implementation GetSchedule 

@synthesize appDelegate; 

@synthesize username; 
@synthesize password; 
@synthesize authenticationString; 
@synthesize encodedLoginData; 
@synthesize schedulesArray; 

@synthesize url = _url; 
@synthesize statusCode = _statusCode; 
@synthesize data = _data; 
@synthesize error = _error; 
@synthesize isExecuting = _isExecuting; 
@synthesize isFinished = _isFinished; 

+ (id)urlDownloaderWithUrlString:(NSString *)urlString { 

NSURL * url = [NSURL URLWithString:urlString]; 
GetSchedule *operation = [[self alloc] initWithUrl:url]; 
return [operation autorelease]; 
} 

- (id)initWithUrl:(NSURL *)url { 

self = [super init]; 
if (self == nil) 
    return nil; 

_url = [url copy]; 
_isExecuting = NO; 
_isFinished = NO; 

return self; 
} 

- (void)dealloc 
{ 
[username release]; 
[password release]; 
[encodedLoginData release]; 

[_url release]; 
[_connection release]; 
[_data release]; 
[_error release]; 
[super dealloc]; 
} 

- (BOOL)isConcurrent 
{ 
return YES; 
} 

- (void)start 
{ 
if (![NSThread isMainThread]) 
{ 
    [self performSelectorOnMainThread:@selector(start) withObject:nil waitUntilDone:NO]; 
    return; 
} 
self.username = appDelegate.username; 
self.password = appDelegate.password; 

Authentication *auth = [[Authentication alloc] init]; 
authenticationString = (NSMutableString*)[@"" stringByAppendingFormat:@"%@:%@", username, password];  
self.encodedLoginData = [auth encodedAuthentication:authenticationString]; 
[auth release]; 

NSLog(@"operation for <%@> started.", _url); 

[self willChangeValueForKey:@"isExecuting"]; 
_isExecuting = YES; 
[self didChangeValueForKey:@"isExecuting"]; 

// Setup up the request with the url 
NSMutableURLRequest *request = [[NSMutableURLRequest alloc] 
           initWithURL:_url]; 

[request setHTTPMethod:@"GET"]; 
[request setValue:[NSString stringWithFormat:@"Basic %@", encodedLoginData] forHTTPHeaderField:@"Authorization"]; 

_connection = [[NSURLConnection alloc] initWithRequest:request 
               delegate:self]; 
if (_connection == nil) 
    [self finish]; 
else { 
    _data = [[NSMutableData alloc] init]; 
} 

} 

    - (void)finish 
{ 
NSLog(@"operation for <%@> finished. " 
     @"status code: %d, error: %@, data size: %u", 
     _url, _statusCode, _error, [_data length]); 

[_connection release]; 
_connection = nil; 

[self willChangeValueForKey:@"isExecuting"]; 
[self willChangeValueForKey:@"isFinished"]; 

_isExecuting = NO; 
_isFinished = YES; 

[self didChangeValueForKey:@"isExecuting"]; 
[self didChangeValueForKey:@"isFinished"]; 
} 

#pragma mark - 
#pragma mark NSURLConnection delegate 

- (void)connection:(NSURLConnection *)connection 
didReceiveResponse:(NSURLResponse *)response 
{ 
//[_data release]; 
//_data = [[NSMutableData alloc] init]; 

[_data setLength:0]; 

NSHTTPURLResponse * httpResponse = (NSHTTPURLResponse *)response; 
_statusCode = [httpResponse statusCode]; 
} 

- (void)connection:(NSURLConnection *)connection 
didReceiveData:(NSData *)data 
{ 
[_data appendData:data]; 
} 

- (void)connectionDidFinishLoading:(NSURLConnection *)connection 
{ 
// Parse the responseData of json objects retrieved from the service 
SBJSON *parser = [[SBJSON alloc] init]; 

NSString *jsonString = [[NSString alloc] initWithData:_data encoding:NSUTF8StringEncoding]; 
NSDictionary *jsonData = [parser objectWithString:jsonString error:nil]; 
NSMutableArray *array = [jsonData objectForKey:@"Children"]; 

schedulesArray = [NSMutableArray array]; 
[schedulesArray addObject:array]; 

// Callback to AttendanceReportViewController that the responseData finished loading 
[attendanceReportViewController loadSchedule]; 

[self finish]; 

} 

- (void)connection:(NSURLConnection *)connection 
didFailWithError:(NSError *)error 
{ 
_error = [error copy]; 
[self finish]; 
} 

@end 

當收到所有數據時,我想回到我的ViewController並獲取所有請求中的所有數據的數組。

+0

我推薦[ASIHTTPRequest](http://allseeing-i.com/ASIHTTPRequest/)lib,很容易用它排隊多個請求。轉到頁面並選擇如何使用它,然後搜索**使用隊列**。 – 2011-05-21 09:28:50

+0

@Nick好的謝謝,但從這我可以創建一個隊列,而不使用ASIHTTP。我並沒有將請求作爲附加結果添加到同一個集合中的問題。但是我想,從一開始就不使用** ASIHTTP **的時候,我的腦袋裏冒出了一些水。我可能需要附加收到的數據,而不是爲每個連接創建一個新的** NSData **實例。 – Silversnail 2011-05-21 09:43:27

+0

我剛剛建議使用ASIHTTP,因爲它比NSURLConnections更易於使用。不過,合併結果應該不成問題,當調用委託方法requestFinished時,只需使用responseString,最終解析並填充模型。 – 2011-05-21 09:46:14

回答

0

創建一個下載

  1. 創建使用NSURLConnection的一個下載器類。
  2. 保留名爲downloaderObjectId的成員變量。
  3. 爲此對象編寫委託方法。該方法將下載的數據和downloaderObjectId傳回給委託。

在委託中。

  1. 與該downloaderObjectId獨特的價值創建多個下載對象(根據你的ncessity)。

  2. 存放在的NSMutableDictionary

  3. 重點爲每個對象,這些對象將被downloaderObjectId。以便下載後調用委託方法時,使用此項從NSMutableDictionary中取回確切的對象。

要點。

  1. 每次調用委託時。你應該從字典中刪除對象(對象完成下載並調用他的delgate,你可以通過他保存的關鍵字downloaderObjectId來識別這個對象。)

  2. 然後檢查字典的數量。如果它是零,你可以確保你的下載完成。所以你可以調用你的viewcontroller。