AsncTask减慢了主(UI)线程

时间:2014-03-13 08:43:58

标签: android multithreading android-asynctask user-experience

我正在开发一款需要解析相当数量的XML和/或JSON的Android应用。

每个文件需要3-4秒才能解析,这是在AsyncTask中完成的。然后将解析后的数据插入到我的SQlite数据库中。

我的问题是在解析过程中UI变得非常缓慢且无响应。

我已经验证过,使用DDMS几乎所有的CPU都需要进行解析,这种情况发生在另一个(AsyncTask)线程中。

我主要测试一个缓慢但有两个核心的星系连接。因此,我不明白为什么我遇到这种UI减速。我仍然可以感受到Nexus 7 2013的速度放缓,但这不是一个问题

您是否知道我如何才能找到解决此问题的原因?当有两个核心可用时,是否有可能在AsyncTask上负载过重而不会出现滞后的UI?

代码示例

下面的第一部分启动了Volley并请求了许多XML文件。

public static void start_update(final Context context,
        Subscription subscription) {
    if (updateConnectStatus(context) == NO_CONNECT)
        return;

    mContext = context;

    RequestManager.initIfNeeded(context);
    RequestQueue requestQueue = RequestManager.getRequestQueue();

    Cursor subscriptionCursor = Subscription.allAsCursor(context
            .getContentResolver());

    while (subscriptionCursor.moveToNext()) {

        Subscription sub = Subscription.getByCursor(subscriptionCursor);

        if (subscription == null || sub.equals(subscription)) {

            StringRequest jr = new StringRequest(sub.getUrl(),
                    new MyStringResponseListener(context
                            .getContentResolver(), sub),
                    createGetFailureListener());

            int MY_SOCKET_TIMEOUT_MS = 300000;
            DefaultRetryPolicy retryPolicy = new DefaultRetryPolicy(
                    MY_SOCKET_TIMEOUT_MS,
                    DefaultRetryPolicy.DEFAULT_MAX_RETRIES,
                    DefaultRetryPolicy.DEFAULT_BACKOFF_MULT);
            jr.setRetryPolicy(retryPolicy);

            // Add the request to Volley
            requestQueue.add(jr);
            processCounts.incrementAndGet();

        }
    }
    requestQueue.start();
}

当Volley获取XML文件时,将调用以下回调:

static class MyStringResponseListener implements Listener<String> {

    static FeedHandler feedHandler = new FeedHandler();
    Subscription subscription;
    ContentResolver contentResolver;
    final JSONFeedParserWrapper feedParser = null;

    public MyStringResponseListener(ContentResolver contentResolver,
            Subscription subscription) {
        this.subscription = subscription;
        this.contentResolver = contentResolver;
    }

    @Override
    public void onResponse(String response) {


        new ParseFeedTask().execute(response); // Execute the parsing as a AsyncTask
    }

    private class ParseFeedTask extends AsyncTask<String, Void, Void> {
        protected Void doInBackground(String... responses) {

            Subscription sub = null;
            String response = responses[0];
            try {
                sub = feedHandler.parseFeed(contentResolver, subscription,
                        response.replace("", "")); // Remove the Byte Order Mark
            } catch (SAXException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            } catch (IOException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            } catch (ParserConfigurationException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            } catch (UnsupportedFeedtypeException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
            return null;
        }

        protected void onPostExecute(Long result) {
            decrementProcessCount();
        }
    }


}

1 个答案:

答案 0 :(得分:3)

Android设备通常具有较差的存储I / O性能,如果主线程因任何原因需要访问驱动器,那么事情可能会变得缓慢。存储是瓶颈,而不是核心数量。

Use the profiler确切了解哪些方法很慢。您可能会发现UI无法从驱动器加载数据。例如,通常在UI线程上加载位图,并且在正常情况下从不注意滞后。在这种情况下,将所有I / O操作移出UI线程,就像您在后台数据处理器中一样。