Objective c 从NSURLResponse完成块中获取数据

Objective c 从NSURLResponse完成块中获取数据,objective-c,ios,nsurlconnection,objective-c-blocks,Objective C,Ios,Nsurlconnection,Objective C Blocks,看起来我还没有完全理解积木的概念 在我的代码中,我必须从“outer”方法返回的asycronous块中取出JSON数据。我在谷歌上搜索发现,如果用块定义一个变量,该变量的v、I、s、I、b、I、l、I、t、y可变性扩展到块 但由于某种原因,返回的json对象为零。我想知道为什么 - (NSMutableDictionary *)executeRequestUrlString:(NSString *)urlString { __block NSMutableDictionary *json =

看起来我还没有完全理解积木的概念

在我的代码中,我必须从“
outer
”方法返回的
asycronous块
中取出JSON数据。我在谷歌上搜索发现,如果用块定义一个
变量,
该变量的v、I、s、I、b、I、l、I、t、y
可变性扩展到

但由于某种原因,返回的json对象为零。我想知道为什么

- (NSMutableDictionary *)executeRequestUrlString:(NSString *)urlString
{
__block NSMutableDictionary *json = nil;
NSURL *url = [NSURL URLWithString:urlString];
NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url];

[request setHTTPShouldHandleCookies:YES];
[request setHTTPMethod:@"GET"];
[request setValue:@"application/x-www-form-urlencoded" forHTTPHeaderField:@"Content-type"];

NSString *cookieString = [self.userDefaults objectForKey:SAVED_COOKIE];

[request addValue:cookieString forHTTPHeaderField:@"Cookie"];

[NSURLConnection sendAsynchronousRequest:request
                                   queue:[NSOperationQueue currentQueue]
                       completionHandler:^(NSURLResponse *response, NSData *data, NSError *error)
                       {

                           NSLog(@"dataAsString %@", [NSString stringWithUTF8String:[data bytes]]);

                           NSError *error1;
                           NSMutableDictionary * innerJson = [NSJSONSerialization
                                   JSONObjectWithData:data
                                              options:kNilOptions
                                                error:&error1];
                           json = innerJson;

                       }];

    return json;
}

调用
sendAsynchronousRequest:queue:completionHandler:
时,您已经请求了一个异步请求。因此,它将请求和块排队,并立即返回。在将来的某个时间点发出请求,然后运行完成块。但到那时,
returnjson
已经运行很久了


如果希望能够同步返回数据,则必须发出同步请求。这将挂起此线程直到它完成,因此它不能是主线程。

首先,回答您的问题:

但由于某种原因,返回的json对象是
nil
。我想知道为什么

- (NSMutableDictionary *)executeRequestUrlString:(NSString *)urlString
{
__block NSMutableDictionary *json = nil;
NSURL *url = [NSURL URLWithString:urlString];
NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url];

[request setHTTPShouldHandleCookies:YES];
[request setHTTPMethod:@"GET"];
[request setValue:@"application/x-www-form-urlencoded" forHTTPHeaderField:@"Content-type"];

NSString *cookieString = [self.userDefaults objectForKey:SAVED_COOKIE];

[request addValue:cookieString forHTTPHeaderField:@"Cookie"];

[NSURLConnection sendAsynchronousRequest:request
                                   queue:[NSOperationQueue currentQueue]
                       completionHandler:^(NSURLResponse *response, NSData *data, NSError *error)
                       {

                           NSLog(@"dataAsString %@", [NSString stringWithUTF8String:[data bytes]]);

                           NSError *error1;
                           NSMutableDictionary * innerJson = [NSJSONSerialization
                                   JSONObjectWithData:data
                                              options:kNilOptions
                                                error:&error1];
                           json = innerJson;

                       }];

    return json;
}
返回的变量在返回时尚未设置。在
sendAsynchronousRequest:queue:completionHandler:
方法返回后,您无法立即获取结果:调用必须在返回块和设置
json
变量之前完成往返

现在请简要说明如何处理:您的方法正在尝试将异步调用转换为同步调用。如果可以的话,尽量保持异步。不要期望一个方法返回一个
NSMutableDictionary*
,而是创建一个方法,该方法获取自己的块,并在
sendAsynchronousRequest:
方法完成时将字典传递给该块:

- (void)executeRequestUrlString:(NSString *)urlString withBlock:(void (^)(NSDictionary *jsonData))block {
    // Prepare for the call
    ...
    // Make the call
    [NSURLConnection sendAsynchronousRequest:request
                                    queue:[NSOperationQueue currentQueue]
                        completionHandler:^(NSURLResponse *response, NSData *data, NSError *error) {
        NSLog(@"dataAsString %@", [NSString stringWithUTF8String:[data bytes]]);
        NSError *error1;
        NSMutableDictionary * innerJson = [NSJSONSerialization
            JSONObjectWithData:data options:kNilOptions error:&error1
        ];
        block(innerJson); // Call back the block passed into your method
        }];

}

使用以下代码转换来自服务器的数据时,请检查字符串:

 NSLog(@"dataAsString %@", [NSString stringWithUTF8String:[data bytes]]);
如果字符串采用正确的JSON格式,那么JSON对象才是正确的

希望这次和平