如果操作未完成,iPhone App会与dispatch_async崩溃

时间:2014-02-19 09:17:55

标签: ios iphone objective-c dispatch-async

在我的运送iPhone App中,我使用了dispatch_async块没有问题。该应用程序检查网站的价格更新,解析HTML,相应地更新核心数据模型,然后刷新正在查看的表。

在我最新的应用程序中,我发现在价格更新过程正在运行时,我可以通过关闭应用程序来崩溃应用程序。第一次和第二次使用之间的差异在我看来只是因为我从表refreshController调用了调度块(即。tableViewController现在内置的pull-to-refresh机制)现在这是iOS7。

有人可以告诉我dispatch_async如何在已知条件下优雅地中止,例如希望停止流程的用户,或者他们切换这样的应用程序并且我想截取该活动来管理块好吗,拜托?

如果有任何关于积极做什么和不做的好背景阅读,我也很高兴看到这样的链接 - 谢谢!

这是我正在使用的(主要是样板文件)dispatch_async代码,为了您的方便:

priceData = [[NSMutableData alloc]init];     // priceData is declared in the header
priceURL = …     // the price update URL

NSURL *requestedPriceURL = [[NSURL alloc]initWithString:[@“myPriceURL.com”]];
NSURLRequest *urlRequest = [NSURLRequest requestWithURL:requestedPriceURL];

dispatch_queue_t dispatchQueue = dispatch_queue_create("net.fudoshindesign.loot.priceUpdateDispatchQueue", NULL);   //ie. my made-up queue name
dispatch_async(dispatchQueue, ^{
        dispatch_async(dispatch_get_main_queue(), ^{
            NSURLConnection *conn = [[NSURLConnection alloc]initWithRequest:urlRequest delegate:self startImmediately:YES];
            [conn start];
        })
});

3 个答案:

答案 0 :(得分:2)

那个样板代码看起来很无用。

您创建一个串行队列。您在队列上调度一个块,除了在主队列上调度块之外什么都不做。您也可以直接在主队列上调度。

答案 1 :(得分:1)

虽然您有一个异步块但是您正在该块中的主线程上执行NSURLConnection请求,这就是为什么应用程序在进程未完成时崩溃的原因。在后台线程中执行请求。您正在阻止此代码中的主线程。

你可以这样做:

dispatch_queue_t dispatchQueue = dispatch_queue_create("net.fudoshindesign.loot.priceUpdateDispatchQueue", 0);   //ie. your made-up queue name
dispatch_async(dispatchQueue, ^{
        NSURLConnection *conn = [[NSURLConnection alloc]initWithRequest:urlRequest delegate:self startImmediately:YES];
        [conn start];
        ...
        //other code
        ...
        dispatch_async(dispatch_get_main_queue(), ^{
            //process completed. update UI or other tasks requiring main thread   
        });
    });

尝试阅读并练习更多关于GCD的内容。

Grand Central Dispatch (GCD) Reference from Apple Docs

GCD Tutorial

答案 2 :(得分:0)

在调度队列中有显式提供取消。基本上,它将是semaphore

NSOperationQueue (更高级别的抽象,但仍使用下面的GCD构建)支持取消操作。您可以创建一系列NSOperations并将其添加到NSOperationQueue,然后在不需要它完成时将 cancelAllOperations 发送给队列。

有用的链接:

http://www.cimgf.com/2008/02/16/cocoa-tutorial-nsoperation-and-nsoperationqueue/

Dispatch queues: How to tell if they're running and how to stop them