如何从AsyncTask中返回一个值,该值在doInBackground中进行另一个异步调用

时间:2017-11-11 23:07:17

标签: java android android-asynctask

我有一个asyncTask来向youtube API发出请求。我试图从AsyncTask返回数据,但是一旦我执行youtube请求它就会冻结

public class FindPreviousPlaylistTask extends AsyncTask<Void, Void, PlaylistListResponse> {

    @Override
    protected PlaylistListResponse  doInBackground(Void... params) {

            YouTube.Playlists.List playlistsListMineRequest = getYoutube().playlists()
                    .list("snippet,contentDetails")
                    .setMine(true)
                    .setMaxResults(50L);

            ArrayList<Playlist> foundPlaylists = new ArrayList<Playlist>();

            PlaylistListResponse response = playlistsListMineRequest.execute(); //Async call

            return response;

        return null;
    }

}

private PlaylistListResponse getPlaylist(){
   FindPreviousPlaylistTask previousPlaylistTask = new FindPreviousPlaylistTask();
   return previousPlaylistTask.execute().get();
}

AsyncTask的重点是在主线程之外进行youtube调用,但现在我无法返回youtube调用的值。

如果我在没有previousPlaylistTask.execute()的情况下致电.get(),则可以正常使用

2 个答案:

答案 0 :(得分:2)

您的应用程序冻结是因为您正在调用get(),这会使当前线程等待任务完成并获得结果。您应该使用onPostExecure(PlaylistListResponse result)中给出的结果。

public class FindPreviousPlaylistTask extends AsyncTask<Void, Void, PlaylistListResponse> {

    @Override
    protected PlaylistListResponse  doInBackground(Void... params) {

            YouTube.Playlists.List playlistsListMineRequest = getYoutube().playlists()
                    .list("snippet,contentDetails")
                    .setMine(true)
                    .setMaxResults(50L);

            ArrayList<Playlist> foundPlaylists = new ArrayList<Playlist>();

            PlaylistListResponse response = playlistsListMineRequest.execute(); //Async call

            return response;

        return null;
    }

    @Override
    protected void onPostExecute(PlaylistListResponse result) {
        // Do something with your result
    }

}

答案 1 :(得分:2)

您返回结果将在onPostExecute()方法中可用,或者您可以创建这样的接口

 public class FindPreviousPlaylistTask extends AsyncTask<Void, Void, 
  PlaylistListResponse> {

   public interface AsyncResponse {
         void processFinish(PlaylistListResponse output);
      }
  public AsyncResponse delegate = null;

   public FindPreviousPlaylistTask (AsyncResponse delegate){
    this.delegate = delegate;
    }

    @Override
    protected PlaylistListResponse  doInBackground(Void... params) {

        YouTube.Playlists.List playlistsListMineRequest = 
     getYoutube().playlists()
                .list("snippet,contentDetails")
                .setMine(true)
                .setMaxResults(50L);

        ArrayList<Playlist> foundPlaylists = new ArrayList<Playlist>();

        PlaylistListResponse response = playlistsListMineRequest.execute(); 
     //Async call

        return response;

     return null;
 }

 @Override
 protected void onPostExecute(PlaylistListResponse result) {
    delegate.processFinish(result);
  }

}

你可以这样称呼它

private void getPlaylist(){

  FindPreviousPlaylistTask previousPlaylistTask=new 
    FindPreviousPlaylistTask( new AsyncResponse(){
    @Override
    void processFinish(PlaylistListResponse output){
        //here your AsyncTask response will be available in output valiable
        //you can do whatever you want here
     }

  }).execute();

}