2012-02-27 64 views
3

我是Android新手。我想問你們有關Asynctask的事情。我有一個活動顯示項目的(應用程序,歌曲,故事..)詳細信息。它需要許多相關數據,例如屏幕截圖,相關應用程序(歌曲,故事)......所以Asynctask的最佳實現是什麼?我是否爲每個任務創建一個asynctask(例如:2 asynctask:1用於獲取屏幕截圖,1用於獲取相關項目...)或者將所有內容放在doInBackGround併發布進度?如何有效使用Asynctask

在此先感謝。

+0

爲了您的任務最好使用隨時可用的庫:http://code.google.com/p/libs-for-android/wiki/ImageLoader – Yahor10 2012-02-27 07:43:37

+0

感謝我已經使用googletv imageloader爲我的應用程序:D – 2012-02-27 10:59:40

回答

2

從OO的角度來看,業務邏輯的東西應該始終與UI的東西隔離。我會隔離和集中我的所有業務調用,比如getSong(),getStore()等爲POJO,並讓我的活動類只專注於UI操作/渲染,這是我要做的事:

  1. 定義接口IBusinessDAO
  2. 定義RealBusinessDAO實現IBusinessDAO
  3. 定義MockBusinessDAO實現IBusinessDAO
  4. 呼叫IBusinessDAO.getSong();裏面AsyncTask.doInBackground()因此,在每個不同的活動中您的AsyncTask實現

    public class MyActivity extends Activity { 
        IBusinessDAO businessDAO; 
    
        ... ... 
    
        private class MyAsyncTask extends AsyncTask<Void, Void, Void> { 
        ... ...   
    
        protected void doInBackground(Void... params) { 
         businessDAO.getSong(); 
        } 
        } 
    
        ... ... 
    
        public void onCreate(Bundle savedInstanceState) { 
        if (runInTest) 
         businessDAO = new MockBusinessDAO(); 
        else 
         businessDAO = new RealBusinessDAO(); 
    
        new myAsyncTask().execute(); 
        } 
    
    } 
    

,您AsyncTask.doInBackgroud()將是簡潔明快,從而使您的代碼更高效,更易於維護。

它還有助於提高代碼的可測試性,爲您的業務邏輯進行單元測試,因爲它是POJO,您可以使用純粹的JUnit編寫測試用例。有時候我們想測試UI組件,並且我們並不關心底層業務邏輯是如何實現的,例如,我的業務邏輯連接到遠程http服務器下載一些json數據,我不想每次都只是這樣做想要測試UI佈局,對於這種情況,我可以輕鬆地更改我所有的活動,使用MockBusinessDAO(類似於Spring的DI概念),測試UI組件,而無需考慮如何實現實際的業務邏輯。

最後,它還提高了代碼的可重用性,因爲您的businesDAO與Andriod沒什麼關係,不像經典的POJO,此外,您不需要關注您的BusinessDAO實現中的任何併發性,因爲所有方法都將在內部調用AsyncTask.doInBackground()方法。

希望有所幫助。

+0

可能是我沒有解釋清楚。我的應用程序以某種方式喜歡Android Market。例如:詳細的應用程序活動,它顯示應用程序截圖,相同類別的應用程序,相同的提供商應用程序,推薦應用程序**所以我創建4個asynctasks來獲取數據或將4個函數放在一個asynctask中,並通過調用publishProgress **來更新UI。哪種方式更有效。我已經有了不同的歌曲,應用程序,故事模式......和假數據:D – 2012-02-27 09:16:08

+0

就個人而言,我更喜歡帶有publishProgress的單個AsyncTask,只要所有耗時的任務都在後臺線程中處理,使用其中一個就足夠且更高效,可以使用其中的幾個。 – yorkw 2012-02-27 09:33:35

1

我曾經在一個實施這種類型的任務的AsyncTask

private void _initCommonAsyncTask(AsyncTaskName currentTaskName, 
     String searchQuery) { 
    CommonAsyncTask task = new CommonAsyncTask(currentTaskName, searchQuery); 
    task.execute(); 
    taskReference = new WeakReference<CommonAsyncTask>(task); 
} 

/** 
* Asynchronous Task for different functionalities. 
* 
*/ 
private class CommonAsyncTask extends AsyncTask<Void, Void, Void> { 
    private final String searchQuery; 
    private AsyncTaskName currentTaskName; 

    /** 
    * Default constructor 
    */ 
    public CommonAsyncTask(AsyncTaskName currentTaskName, String searchQuery) { 
     super(); 
     this.searchQuery = searchQuery; 
     this.currentTaskName = currentTaskName; 
    } 

    @Override 
    protected void onPostExecute(Void result) { 
     switch (currentTaskName) { 
     case SEARCH: 
      // Reinitialized the list view 
      break; 
     case REFRESH: 
      // Reinitialized the list view 
      break; 
     case LOAD_NEXT: 
      // Reinitialized the list view 
      break; 
     default: 
      break; 
     } 
     super.onPostExecute(result); 
    } 

    @Override 
    protected void onPreExecute() { 
     super.onPreExecute(); 
    } 

    @Override 
    protected Void doInBackground(Void... params) { 
     switch (currentTaskName) { 
     case SEARCH: 
      // My searching stuff here 
      break; 
     case REFRESH: 
      // my refreshing stuff here 
      break; 
     case LOAD_NEXT: 
      //my load next 50 orders here 
      break; 
     default: 
      break; 
     } 
     return null; 
    } 
} 

可以使用

_initCommonAsyncTask(AsyncTaskName.SEARCH, searchQuery); 

調用的AsyncTask定義枚舉您的任務列表這樣

public enum AsyncTaskName { 
    SEARCH, REFRESH, LOAD_NEXT; 
}