【发布时间】:2014-04-30 20:43:37
【问题描述】:
我有一个AsyncTask,它接收上下文(使用onPostExecute)并运行doInBackground 以从服务器返回对象的ArrayList。当我执行这个时,我可以看到doInBackground 运行良好,但是它没有将结果传递给onPostExecute。
经过大量搜索,我还没有找到关于如何在AsyncTask 中返回对象的 ArrayList 的答案。
这是我在doInBackground 中使用onPostExecute 创建的对象:
public class ServerTimeCard {
public String eventNameInput;
Boolean isLocation, isImage, isVoice;
public ServerTimeCard(String eventNameInput, boolean isLocation, boolean isImage, boolean isVoice) {
this.eventNameInput = eventNameInput;
this.isLocation = isLocation;
this.isImage = isImage;
this.isVoice = isVoice;
}
}
我在onCreate 中执行AsyncTask 和new LoadFriendCards(context).execute();。
预期输出:
doInBackground应该返回一个 ArrayList 到onPostExecute当前输出:
onPostExecute中的ArrayList<ServerTimeCard>的大小为零,而doInBackground中的相同arraylist 具有更大的大小。
以下是AsyncTask代码。
public class LoadFriendCards extends AsyncTask<Void, Void, ArrayList<ServerTimeCard>> {
Context context;
ArrayList<ServerTimeCard> result;
public LoadFriendCards(Context context) {
this.context = context;
}
@Override
protected ArrayList<ServerTimeCard> doInBackground(Void... voids) {
result = new ArrayList<ServerTimeCard>();
// ...a bunch of data retrieval goes on here...
// querying parse for object info
// adding a new object to the local ArrayList for all in db
for (String friend : friendsListNames) {
ParseQuery<ParseObject> query = ParseQuery.getQuery("TestObject");
query.whereEqualTo("accountName", friend+"@gmail.com");
query.findInBackground(new FindCallback<ParseObject>() {
public void done(List<ParseObject> objects, ParseException e) {
if (e == null) {
for (ParseObject cardInfo : objects) {
ServerTimeCard item = new ServerTimeCard(
cardInfo.getString("eventName"),
cardInfo.getBoolean("isImage"),
cardInfo.getBoolean("isImage"),
cardInfo.getBoolean("isVoice"));
result.add(item);
Log.e("New item called: ", String.valueOf(item.eventNameInput));
Log.e("New size of array...", String.valueOf(result.size()));
}
} else {
Log.d("info", "Error: " + e.getMessage());
}
}
});
}
// returning the new ArrayList<ServerTimeCard> to onPostExecute
// PROBLEM: THE SIZE OF THE RESULT IS 0
Log.e("Size of passing array", String.valueOf(result.size()));
return result;
}
@Override
protected void onPostExecute(ArrayList<ServerTimeCard> result) {
// PROBLEM: This returns 0
Log.e("Data list size: ", String.valueOf(result.size()));
// trying to use all objects in the arraylist here but it doesn't work
// due to the size. Something isn't passing correctly.
}
}
Log.e 的 Logcat 输出:(看起来它调用了 doInBackground,然后是 onPostExecute,然后又是 doInBackground)
E/Size of passing array﹕ 0
E/Data list size:﹕ 0
E/New item called:﹕ yah
E/New size of array...﹕ 1
E/New item called:﹕ lplokolol
E/New size of array...﹕ 2
E/New item called:﹕ It works
E/New size of array...﹕ 3
已解决:我最初认为我需要 AsyncTask,但我最终将其全部删除并将所有代码放入我的 Main 类中的一个方法中。我在 asynctask 中一次运行了太多东西,并且结构将数据扔到了各处。经验教训:保持简单。
【问题讨论】:
-
你能展示一下实际的循环吗?似乎每次迭代都在创建一个新列表,但没有循环就无法判断。
-
如果您将日志语句放在 doInBackground 方法中的
return result之前,输出会是什么? -
@zmbq 添加了 for 循环。我正在 Parse 中查询对象并将它们添加到数组列表中。
-
当你在doInBackground中下断点时,result什么时候会自行重置?
-
另外,在
result.add(item);之后添加日志以确保item != null并在添加后立即查看result.size()。
标签: java android arraylist android-asynctask closures