IOS 后台任务、多任务的理解1
情况1:
应用在前台一直进行着某项耗时任务(数据库操作,网络文件下载、上传等)切换到后台后,但仍需保持该任务的继续执行直到结束
情况2:
应用本身已切换至后台,但需时不时的去执行某个任务(更新用户位置、网络获取点信息等,但建议该任务不应是相当耗时的处理,我们无法预测操作系统给你此次后台任务的执行时间),并将获取的数据保存或更新应用的某些页面,然后推送唤醒应用。当用户打开app时,界面或状态已是最新状态(IOS7的最新后台任务用处)
http://onevcat.com/2013/08/ios7-background-multitask/
其实对于上述两种情况都可以用于一些耗时操作,比如大文件下载,只要处理好前一次请求真正断开后才真正开始后台任务的重新断点续传,关键是在于保证所已下载的不完整文件不包含重复的或少的字节数
从4.0开始:
一般在app代理函数appDidEnterBackground中有5s的时间给你(5s也不一定,反正是个不长的时间,不过对于是执行一个for
while循环之类的一大坨代码,5s左右的时间是绝对够用的,计算机的速度还是蛮快的嘛,除非是一些相当耗时的操作,如下载、数据库远程查询等),如果不够则应采用下面的方式
[[NSNotificationCenter
defaultCenter] addObserver:self selector:@selector(doUpdate)
name:UIApplicationDidEnterBackgroundNotification
object:nil]; //程序进入后台后开始执行后台操作函数
注意:在开始doUpdate函数前应保证接续的任务前段完全close,特别对于文件下载,可以先执行断开前面的链接,另外,设置setKeepAliveTimeout后
也不是说拥有无限的后台执行时间,需要特意指定app的类型,后面有讲,当然这样就只能在越狱环境下玩了
- (void) doUpdate{
[self
backgroundHandler]; //每个应用程序本身就有600秒即10分钟的后台执行时间
//setKeepAliveTimeout
设置600秒的超时之后开始执行backgroundHandler函数,且超时时间必须大于等于600秒,当本身的600耗费完后便重新被唤醒执行,但此次唤醒执行的时间大约只有1分钟,所以这里到后面会出现“唤醒后只执行大约1分钟,然后要再等9分钟这个setKeepAliveTimeout才会重新起作用,即又唤醒程序,这之间就有一个间歇时间段了”
(可以用-backgroundTimeRemaining属性来返回剩余时间)
BOOL backgroundAccepted = [[UIApplication sharedApplication] setKeepAliveTimeout:600 handler:^{ [self backgroundHandler]; }];
if
(backgroundAccepted)
{
NSLog(@"backgrounding accepted");
}
}
- (void)backgroundHandler {
NSLog(@"###
-->backgroundinghandler");
UIApplication*
app = [UIApplication sharedApplication];
self.backgroundUpdateTask = [app
beginBackgroundTaskWithExpirationHandler:^{
[app endBackgroundTask:self.backgroundUpdateTask];
self.backgroundUpdateTask = UIBackgroundTaskInvalid;
}];//这段很关键,beginBackgroundTaskWithExpirationHandler是开启后台任务执行,这个方法调用之后,后面的任务代码才能开始执行 ,上面有说ios程序默认有10分钟的后台执行时间,但是前提是要beginBackgroundTaskWithExpirationHandler下之后,直接写后台执行代码是没作用的, 其中闭包中的代码表示每开启一个后台任务之后结束时要对应结束该任务
............耗时操作请求
}
注意点:
1.setKeepAliveTimeout函数成功调用后,在程序生命周期内有效。
该函数的效果在回到前台的状况下,依然有效。因此在applicationWillEnterBackground函数里要用clearKeepAliveTimeout函数用来清除handler,避免重复
2. 唤醒app的时间间隔是不精准的。
3.对于任务代码,其实质是在beginBackgroundTaskWithExpirationHandler之后开始新的后台任务,而不能理解为app活动状态就在执行的任务的继续执行,即app在活动状态下有一直在进行某项事宜,当home一下,此事项就立马被挂起了,如果你想此任务能继续执行,只有在beginBackgroundTaskWithExpirationHandler重新写该事项的执行代码,比如下载,你可以在任务代码里先获取下之前已下载的包的大小,然后再重新请求NSURLConnection断点续传
4.对于之上的操作,系统可能无法保持无限的后台执行,所以这里可以采取如下方式,不过可能无法通过appstore审核:
有5类app允许有“无限的”后台运行时间:
你可以将任何app声明为上述5种类型以获得无限的后台运行时间
参考网址:http://blog.csdn.net/kmyhy/article/details/7940714
相关补充:
在Info.plist文件中指定或添加UIBackgroundModes键(直接输入后系统会将该键变为Required
background modes),其类型为一个array,包含子项为字符串,可以为voip、location、voip(注意这些值在你输入后系统会自动变更为其它的值,例如你输入location,系统会将其变为App
registers for location
updates,当然你也可以直接选择系统提供的项,只是注意这里写的值和系统给的值字面上是不一样的)
情况2:
http://onevcat.com/2013/08/ios7-background-multitask/
从4.0开始:
BOOL backgroundAccepted = [[UIApplication sharedApplication] setKeepAliveTimeout:600 handler:^{ [self backgroundHandler]; }];
}
注意点:
相关补充:
if(![UIDevice currentDevice].multitaskingSupported){
}
网络上志同道合,我们一起学习网络安全,一起进步,QQ群:694839022