如果AsyncTask不是内部类...... - 一些问题

时间:2011-08-26 14:11:24

标签: android android-asynctask

1)我并不感到不安,为什么Android的样本几乎都使用AsyncTasks作为私有内部类。我知道让它成为内部类很方便,但是它使我们的类文件更长,更难阅读。 ShelvesActivity of Shelves样品应用甚至有845行。难道你不认为这是一个糟糕的设计或糟糕的建筑吗?

2)如果我创建了我的ScanStorageTask外部类,我需要传递给它什么?整个活动或仅使用小部件?

示例:如果我必须在ScanStorageTask中使用WebView,Button和ProgressBar。 我用这个:

ScanStorageTask task = new ScanStorageTask(this); // "this" is activity reference, then get the webView, button, progressBar from it.

或者这个:

ScanStorageTask task = new ScanStorageTask(webView, button, progressBar);

4 个答案:

答案 0 :(得分:14)

从外部做这件事并没有错,实际上它可能是一个更好的设计。传递UI元素是一种紧密耦合,当你拥有一个非常庞大的代码库时会让你陷入麻烦。

为什么不在外部使用并使用UI控件使用的“监听器”模式?使您的ScanStorageTask成为自己的类,使用onComplete方法创建一个OnCompleteListener接口,并将其传递给您的ScanStorageTask实例(公开一个setOnCompleteListener方法或类似的东西)。然后,onPostExecute可以这样做:

if(onCompleteListener != null)
  onCompleteListener.onComplete(data);

这样,您可以根据数据在活动中定义UI更新。它可以更好地分离关注点,并且可以保持每个类的代码行数,因为这似乎是您更喜欢的。如果您还没有这个,请创建一个表示您需要传入和传出的数据的类,这就是您作为执行方法的参数传递给任务的内容以及onPostExecute传递给onComplete的内容。

答案 1 :(得分:6)

内部类允许您在ActivityonPreExecute()onPostExecute()内部操作外部onProgressUpdate()的UI,而无需将整个UI结构传递给AsyncTask。您只能使用活动功能。

这很有用,因为操作UI不是AsyncTask的主要目的。它正在进行非UI后台工作。为此,您通常需要传递的是执行此工作的一些参数(例如,提供URL以下载文件)。

当您声明AsyncTask外部时,您基本上无法访问onPreExecute()内的UI资源(根本没有参数传递给它),而且其他两个UI函数内部非常难。

我认为AsyncTask只是用于作为内部类来进行工作并更新UI线程。请参阅说明:

  

AsyncTask可以正确,轻松地使用UI线程。这个班   允许执行后台操作并在UI上发布结果   线程,而不必操纵线程和/或处理程序。

(来自the class documentation

答案 2 :(得分:4)

我在may应用程序中遇到了同样的问题。我想使用Socket与PC建立通信,我希望我的代码可以从多个活动/片段中重复使用。

首先,我尝试不使用内部类,但是当你必须更新UI时非常方便,所以我找到了另一种解决方案:
我创建了一个外部AsyncTask类,负责与pc通信,我在每个活动/片段中创建了内部类,只重写了onPostExecute()方法。这样我可以重用我的代码并更新UI。

如果您只想获取任务的结果,并且响应性对于您的应用程序不是必不可少的,则可以使用AsyncTask类的get()方法。

答案 3 :(得分:2)

  1. 我个人认为如果你只在一个点上使用类,那么在那里定义它是最可读的 - 因此是anon内部类。

  2. 没关系。从设计角度来看,我只传递实际需要的数据。但是你需要注意一个可能的缺陷 - 当活动实例被取消激活(隐藏或方向改变)并且你的后台线程仍然运行并试图显示一些变化时,你可能会得到各种错误或根本没有显示任何错误。

相关问题