每当我尝试下载UIScrollView
,MPMapView
或其他内容后面的大文件时,只要触摸iPhone屏幕,下载过程就会停止。值得庆幸的是,Jörn上的一篇很棒的博客文章提出了一种替代方法,即使用NSRunLoopCommonModes
进行连接。
这让我详细了解了两种模式,即NSDefaultRunLoopMode和NSRunLoopCommonModes,但是苹果文档没有对它进行友好的解释,除了说
NSDefaultRunLoopMode
NSRunLoopCommonModes
CFRunLoopAddCommonMode
谁能用人类语言解释两者吗?
最佳答案
运行循环是一种机制,允许系统唤醒 sleep 线程,以便它们可以管理异步事件。通常,当您运行一个线程(主线程除外)时,可以选择是否在运行循环中启动该线程。如果线程运行某种排序或长时间运行的操作而没有与外部事件交互且没有计时器,则您不需要运行循环,但是如果您的线程需要响应传入的事件,则应将其附加到运行循环中,以便当新事件到来时唤醒线程。 NSURLConnection
生成的线程就是这种情况,因为它们仅在传入事件(从网络)中唤醒时才唤醒。
每个线程可以与多个运行循环关联,也可以与可以设置为在不同模式下工作的特定运行循环关联。 “运行循环模式”是OS所使用的约定,用于为何时传递某些事件或收集它们以供稍后传递建立一些规则。
通常,所有运行循环都设置为“默认模式”,以建立管理输入事件的默认方式。例如:一旦发生鼠标拖动(Mac OS)或触摸(在iOS上)事件,则此运行循环的模式将设置为事件跟踪;这意味着不会在新的网络事件上唤醒线程,但是这些事件将在以后用户输入事件终止并且运行循环再次设置为默认模式时传递。显然,这是OS架构师做出的选择,即优先考虑用户事件而不是后台事件。
如果决定通过使用NSURLConnection
更改scheduleInRunLoop:forModes:
线程的运行循环模式,则可以将线程分配给特殊的运行循环模式,而不是特定的默认运行循环。包括事件跟踪在内的许多输入源都使用称为NSRunLoopCommonModes
的特殊伪模式。例如,将NSURLConnection
的实例分配给通用模式意味着除了“默认模式”之外,还将其事件与“跟踪模式”相关联。将线程与NSRunLoopCommonModes
关联的一个优点/缺点是线程不会被触摸事件阻塞。
可以将新模式添加到通用模式,但这是一个很底层的操作。
最后,我想补充一些注意事项:
从网络下载的缩略图具有表格 View 。我们可能会认为
在表格 View 处于打开状态时从网络下载这些图像
滚动可以改善用户体验(因为我们可以在
滚动),但这是不利的,因为
滚动会受到很大的影响。在这个带有
NSURLConnection
的示例中,不应使用运行循环。最好使用UIScrollView
委托(delegate)方法来检测滚动何时终止,然后更新表并下载新项目来自网络;
运行循环管理问题。在上面的示例中,您可以
考虑将您的网络请求添加到自定义串行队列中。
关于iphone - NSDefaultRunLoopMode与NSRunLoopCommonModes,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/7222449/