我有一个困惑。根据我的理解,委托(delegate)和完成处理程序是两种不同的机制,可以使用其中任何一种来实现 NSURLSession。 但是为什么下面的委托(delegate)没有被调用
(void)URLSession:(NSURLSession *)session dataTask:(NSURLSessionDataTask *)dataTask didReceiveResponse:(NSURLResponse *)aresponse
但这被称为
- (void)URLSession:(NSURLSession *)session dataTask:(NSURLSessionDataTask *)dataTask didReceiveResponse:(NSURLResponse *)aresponse
completionHandler:(void (^)(NSURLSessionResponseDisposition disposition))completionHandler
与 didReceiveChallenge 类似。
当
(void)URLSession:(NSURLSession *)session dataTask:(NSURLSessionDataTask *)dataTask didReceiveData:(NSData *)data
可以调用,那么需要显式地为 didRecieveResponse 添加完成处理程序吗?
这确实不是必需的还是本来就是这样的?
您能否解释一下在上面和一般情况下添加完成处理程序的目的是什么?
最佳答案
参见 docs for the NSURLSessionDataDelegate尤其是注释:
NOTE
An NSURLSession object need not have a delegate. If no delegate is assigned, when you create tasks in that session, you must provide a completion handler block to obtain the data.
Completion handler block are primarily intended as an alternative to using a custom delegate. If you create a task using a method that takes a completion handler block, the delegate methods for response and data delivery are not called.
因此,如果使用完成处理程序方法,则 NSURLSessionDataDelegate
不会处于事件状态,但 NSURLSessionDelegate
和 NSURLSessionTaskDelegate
可能会处于事件状态。
如果您对连接进行复杂的处理,例如希望将其用作在完成或其他复杂处理之前使用数据的流连接,则委托(delegate)方法是最好的。您将需要定义和创建一个对象来处理任务、跟踪状态以及收到数据后应如何处理。您还需要保留此对象。单个对象可以处理多个连接,但这也会是您需要处理的复杂性。
回调/闭包/ block 方法允许在发出请求的位置定义处理响应和数据的所有逻辑,并在闭包中需要捕获请求时的所有状态。如果您的要求很简单,在我看来,这通常是最好的方法,因为它具有将代码放在一起并且无需担心多个任务及其状态的好处。
关于ios - NSURLSession 中的委托(delegate)和完成处理程序,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32759239/