为什么要使用AsyncTaskLoader和LoaderManager,而不是简单的Handler?

9
在Android开发中,将异步任务从UI线程中运行并修改UI是一个常见的问题,因此我决定花些时间研究和尝试不同的技术,找出最适合我的方法。
我认为以下因素很重要:
- 可靠性 - 代码可读性 - Activity或Fragment应该尽可能保持线程管理的简洁
以下是我对各种方法的印象总结(可能有误,一些只是个人意见):
AsyncTask:
- 当我第一次接触Android时,我使用简单的AsyncTask而没有LoaderManager: - 经常会出现问题,所以我编写了自己的AsyncTaskManager来管理它们和Activity生命周期。 - 这些存在一些限制和内存泄漏问题。 - 最大的问题是它们使我的代码变得非常复杂,简化代码就失去了使用它们的初衷。
带LoaderManager的AsyncTaskLoader:
- 这似乎是推荐的方法,所以我进行了一些研究: - 经过一番了解,似乎这种方法之所以被推荐是因为它使用Fragment生命周期管理任务,并且基本上只是在必要时重新启动任务。如果在Activity重新启动后启动了一个任务,则似乎无法接收其结果。 - 所有任务参数似乎都必须是Parcelable或Serialiazable,以进入Bundle对象。
使用Messages的Handler和Threads:
- 这是我选择的方法: - 它易于实现,极其可定制。 - 您可以访问执行任务的线程:设置优先级、设置线程名称进行调试、设置守护进程等。 - 根据眼睛测试,似乎比使用AsyncTasks更响应,即我点击一个按钮很多次并观察结果和线程闪过;) 我可以基准测试这个。 - 为了处理生命周期问题,可以编写一个单例类来管理消息(在进程存活时持续存在)。当给定Activity的处理程序未设置时,将其存储,然后如果它请求其丢失的消息,则将其转发到Activity处理程序。这意味着任务不必以相同的参数重新启动,这对于不幂等的任务至关重要。
因此,我得出结论,使用Handler、Threads和Messages是一个更好的解决方案,但我确信我错过了什么,因为我几乎在任何地方看到的建议都是使用AsyncTaskLoader方法。我错过了什么?
感谢您的反馈。

“Handler”、“Threads”和“Messages”是构建块。 “AsyncTask”和“LoaderManager”是基于这些构建块构建的,具有特定的用例,并符合大多数已接受的使用模式。因此,在这里,用例非常重要。仅当提供的类不足以完成任务时,您才应该转向自定义解决方案。 - S.D.
我得出的结论是,自定义解决方案更容易实现,并且在几乎所有中等复杂度的情况下提供更多功能和灵活性。 - Emil Davtyan
2个回答

7
你没有意识到的是,像 AsyncTaskLoaderManager 这样的类是针对 Android 设计的。这意味着操作系统被设计成在与桌面电脑相比硬件最小限度下发挥最大作用。由于线程受到更严格的限制,AsyncTask 限制了您的线程池。如果您尝试生成100多个线程,则新线程将被拒绝或崩溃系统。当然,你可以使用 ThreadHandler,但管理它们需要自己独立完成。
据我所知,AsyncTask 最多支持10个线程和10个任务的队列深度(在后来的版本中可能已经增加)。如果这很限制,你总可以自己获取源代码并编写自己的代码。我以前做过。你要考虑的重要问题是,我是否会因生成太多线程而在未来遇到麻烦,如果是,我该如何处理。
至于为什么建议使用 LoaderManagerAsyncTaskLoader,那只是一种方便。这是重新加载数据并将其传递给依赖于该数据的代码部分的简单方法。这并不适用于每种情况。

4

Handler, Threads, 和 Messages 是低级别的类。这给了你很大的灵活性 - 你可以按照自己的需要将它们组合起来解决特定的问题。但是,你还需要处理很多底层的东西,比如停止/启动线程、路由到正确的线程、在重新创建活动时保存/恢复或重新创建实例等。

加载器为你处理了大部分工作,专门设计来解决一个特定的问题 - 在活动中加载数据。最大的优点是,Activity (或 FragmentActivity) 将负责管理和重新启动你的加载器,当活动被重新创建时(如果不造成内存泄漏就很棘手)。它还会缓存数据,因此你不需要自己去做这个事情。尽管如此,如果你想做一些稍微不同的事情,使用 Loaders 可能会变得棘手。所以,如果你需要更大的灵活性,请考虑使用 AsyncTask。如果那还不适合,可以再向下一级使用 ThreadsHandler


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接