AsyncTask在完成内部方法之前完成了doInBackground()

时间:2016-08-25 10:55:06

标签: android android-asynctask vk-sdk

我正在使用Vk Sdk。我创建了AsyncTask来在后台从服务器加载数据。但是,事实证明doInBackground()在其内部的任务完成之前就已完成。代码如下:

@Override
protected Void doInBackground(Void... params) {
    Log.v(TAG, "Before Loading in Background");

    VKRequest request = VKApi.wall().get(VKParameters.from(VKApiConst.OWNER_ID, "-100177655", VKApiConst.OFFSET, "2"));
    request.executeWithListener(new VKRequest.VKRequestListener() {
        @Override
        public void onComplete(VKResponse response) {
            super.onComplete(response);

            String jsonData = response.responseString;
            Log.v(TAG, "json is ready");
            try {
                Log.v(TAG, "before parsing");
                parsePostsData(jsonData);
                Log.v(TAG, "after parsing");
            } catch (JSONException e) {
                Log.v(TAG, "EXCEPTION is thrown");
                e.printStackTrace();
            }
        }
    });

    Log.v(TAG, "Finished Background Tasks");
    return null;
}

我怀疑request.executeWithListener(...)正在创建另一个线程并在那里做必要的工作。因此,AsyncTask认为他的线程中的工作已经完成。但是,我不确定。该方法的文档中没有任何内容。

另一个问题是调用哪个线程onComplete(...)方法正在运行?在由request创建的主要或同一个单独的线程上?

感谢任何帮助:)

2 个答案:

答案 0 :(得分:1)

根据您的代码,您有2个不同的线程被调用。 AsynTask是一个首先执行的后台线程。然后你调用了VKRequest executeWithListener,它将在doInBackground()中创建另一个线程。

要在单个线程中存档,您应该将执行方法更改为VKRequest中的executeSyncWithListener()

@Override
protected Void doInBackground(Void... params) {
    Log.v(TAG, "Before Loading in Background");

    VKRequest request = VKApi.wall().get(VKParameters.from(VKApiConst.OWNER_ID, "-100177655", VKApiConst.OFFSET, "2"));
    request.executeSyncWithListener(new VKRequest.VKRequestListener() {
        @Override
        public void onComplete(VKResponse response) {
            super.onComplete(response);

            String jsonData = response.responseString;
            Log.v(TAG, "json is ready");
            try {
                Log.v(TAG, "before parsing");
                parsePostsData(jsonData);
                Log.v(TAG, "after parsing");
            } catch (JSONException e) {
                Log.v(TAG, "EXCEPTION is thrown");
                e.printStackTrace();
            }
        }
    });

    Log.v(TAG, "Finished Background Tasks");
    return null;
}

希望这会有所帮助!

答案 1 :(得分:0)

做这样的事情:

@Override
protected Void doInBackground(Void... params) {
    Log.v(TAG, "Before Loading in Background");

    VKRequest request = VKApi.wall().get(VKParameters.from(VKApiConst.OWNER_ID, "-100177655", VKApiConst.OFFSET, "2"));
    request.executeWithListener(new VKRequest.VKRequestListener() {
        @Override
        public void onComplete(VKResponse response) {
            super.onComplete(response);

            String jsonData = response.responseString;
            Log.v(TAG, "json is ready");

// YOUR CUSTOM CALLBACK
new Thread(new myCustomRunnable(jsonData)).start();
            try {
                Log.v(TAG, "before parsing");
                parsePostsData(jsonData);
                Log.v(TAG, "after parsing");
            } catch (JSONException e) {
                Log.v(TAG, "EXCEPTION is thrown");
                e.printStackTrace();
            }
        }
    });

    Log.v(TAG, "Finished Background Tasks");
    return null;
}

其中myCustomRunnable是一个实现'Runnable'接口的类。

public class myCustomRunnable implements Runnable{
    private String msg ="";
    public OToast(String msg) {
        this.msg = msg;
    }
    @Override
    public void run() {
//here do anything you want 
Log.v("mylog",msg);
//or even execute code in main thread:
runOnUiThread(new Runnable() {
                @Override
                public void run() {
                    //your code
                }
            });
    }

}

甚至更简单:

 @Override
    protected Void doInBackground(Void... params) {
        Log.v(TAG, "Before Loading in Background");

        VKRequest request = VKApi.wall().get(VKParameters.from(VKApiConst.OWNER_ID, "-100177655", VKApiConst.OFFSET, "2"));
        request.executeWithListener(new VKRequest.VKRequestListener() {
            @Override
            public void onComplete(VKResponse response) {
                super.onComplete(response);

                String jsonData = response.responseString;
                Log.v(TAG, "json is ready");

    // EXECUTE CODE IN MAIN UI THREAD:
final String final_json = jsonData;
runOnUiThread(new Runnable() {
                    @Override
                    public void run() {
                        //your code
textview.setText(final_json);
                    }
                });

                try {
                    Log.v(TAG, "before parsing");
                    parsePostsData(jsonData);
                    Log.v(TAG, "after parsing");
                } catch (JSONException e) {
                    Log.v(TAG, "EXCEPTION is thrown");
                    e.printStackTrace();
                }
            }
        });

        Log.v(TAG, "Finished Background Tasks");
        return null;
    }