2010-11-16 104 views
34

我有一個應用程序做了一些長時間的計算,並且我希望在完成時顯示進度對話框。到目前爲止,我發現我可以用線程/處理程序來完成這個工作,但是沒有工作,然後我發現AsyncTask將參數傳遞給AsyncTask,並返回結果

在我的應用程序中,我使用帶有標記的貼圖,並且實現了onTap函數來調用我定義的方法。該方法使用「是/否」按鈕創建對話框,如果單擊「是」,我想調用AsyncTask。我的問題是如何通過ArrayList<String>AsyncTask(並在那裏工作),以及如何從AsyncTask得到一個新的ArrayList<String>

方法的代碼如下所示:

String curloc = current.toString(); 
String itemdesc = item.mDescription; 

ArrayList<String> passing = new ArrayList<String>(); 
passing.add(itemdesc); 
passing.add(curloc); 

ArrayList<String> result = new ArrayList<String>(); 

new calc_stanica().execute(passing,result); 

String minim = result.get(0); 
int min = Integer.parseInt(minim); 

String glons = result.get(1); 
String glats = result.get(2); 

double glon = Double.parseDouble(glons); 
double glat = Double.parseDouble(glats); 

GeoPoint g = new GeoPoint(glon, glat); 
String korisni_linii = result.get(3); 

所以,你看,我想發送的字符串數組列表「傳遞」到AsyncTask,並得到了「結果」的字符串數組列表返回。而calc_stanica AssycTask類看起來是這樣的:

public class calc_stanica extends AsyncTask<ArrayList<String>, Void, ArrayList<String>> { 
    ProgressDialog dialog; 

    @Override 
    protected void onPreExecute() { 
     dialog = new ProgressDialog(baraj_mapa.this); 
     dialog.setTitle("Calculating..."); 
     dialog.setMessage("Please wait..."); 
     dialog.setIndeterminate(true); 
     dialog.show(); 
    } 

    protected ArrayList<String> doInBackground(ArrayList<String>... passing) { 

     //Some calculations... 

     return something; //??? 
    } 

    protected void onPostExecute(Void unused) { 
     dialog.dismiss(); 
    } 

所以我的問題是如何獲得在AsyncTask doInBackground方法的「傳遞」數組列表中的元素(並使用它們),以及如何返回一個數組列表在主要方法(「結果」數組列表)中使用?

回答

61

改變你的方法是這樣的:

String curloc = current.toString(); 
String itemdesc = item.mDescription; 
ArrayList<String> passing = new ArrayList<String>(); 
passing.add(itemdesc); 
passing.add(curloc); 
new calc_stanica().execute(passing); //no need to pass in result list 

,改變你的異步任務執行

public class calc_stanica extends AsyncTask<ArrayList<String>, Void, ArrayList<String>> { 
ProgressDialog dialog; 

    @Override 
    protected void onPreExecute() { 
     dialog = new ProgressDialog(baraj_mapa.this); 
     dialog.setTitle("Calculating..."); 
     dialog.setMessage("Please wait..."); 
     dialog.setIndeterminate(true); 
     dialog.show(); 
    } 

    protected ArrayList<String> doInBackground(ArrayList<String>... passing) { 
     ArrayList<String> result = new ArrayList<String>(); 
     ArrayList<String> passed = passing[0]; //get passed arraylist 

     //Some calculations... 

     return result; //return result 
    } 

    protected void onPostExecute(ArrayList<String> result) { 
     dialog.dismiss(); 
     String minim = result.get(0); 
     int min = Integer.parseInt(minim); 
     String glons = result.get(1); 
     String glats = result.get(2); 
     double glon = Double.parseDouble(glons); 
     double glat = Double.parseDouble(glats); 
     GeoPoint g = new GeoPoint(glon, glat); 
     String korisni_linii = result.get(3); 
    } 

UPD:

如果你想有機會獲得初始上下文的任務,最簡單的方法是覆蓋onPostExecute到位:

new calc_stanica() { 
    protected void onPostExecute(ArrayList<String> result) { 
     // here you have access to the context in which execute was called in first place. 
     // You'll have to mark all the local variables final though.. 
    } 
}.execute(passing); 
+0

謝謝你的回答,但我還有一件事要問。如果我定義int min = Integer.parseInt(minim);例如,在AsyncTask類onPostExecute()中,我如何從我的主類方法訪問它?當我像這樣改變它時,在主類方法中出現「min不能解決」錯誤。 – 2010-11-16 16:35:18

+2

@Bojan Ilievski:讓你的min變量全局。 – Wroclai 2010-11-16 16:55:25

+0

再次感謝您的答案,我已經解決了我的問題... – 2010-11-16 21:18:31

12

爲什麼要傳遞一個ArrayList? 它應該有可能只是調用直接與PARAMS執行:

String curloc = current.toString(); 
String itemdesc = item.mDescription; 
new calc_stanica().execute(itemdesc, curloc) 

那怎麼varrargs工作,對不對? 使ArrayList傳遞變量是雙重工作。

+0

我非常贊同Leander在這裏。無論如何改變正確的答案複選標記? – 2012-10-23 21:57:40

4

我有點同意利安德在這一個。

電話:

new calc_stanica().execute(stringList.toArray(new String[stringList.size()])); 

任務:

public class calc_stanica extends AsyncTask<String, Void, ArrayList<String>> { 
     @Override 
     protected ArrayList<String> doInBackground(String... args) { 
      ... 
     } 

     @Override 
     protected void onPostExecute(ArrayList<String> result) { 
      ... //do something with the result list here 
     } 
} 

或者您也可以使結果列表中的類參數和一個布爾值(成功/失敗)代替ArrayList的;

public class calc_stanica extends AsyncTask<String, Void, Boolean> { 
     private List<String> resultList; 

     @Override 
     protected boolean doInBackground(String... args) { 
      ... 
     } 

     @Override 
     protected void onPostExecute(boolean success) { 
      ... //if successfull, do something with the result list here 
     } 
} 
1

我不這樣做。我發現更容易重載asychtask類的構造函數..

公共類calc_stanica擴展的AsyncTask>

String String mWhateveryouwantToPass; 

public calc_stanica(String whateveryouwantToPass) 
{ 

    this.String mWhateveryouwantToPass = String whateveryouwantToPass; 
} 
/*Now you can use whateveryouwantToPass in the entire asynchTask ... you could pass in a context to your activity and try that too.*/ ... ... 
0

您可以收到返回結果這樣的: AsyncTask

@Override 
protected Boolean doInBackground(Void... params) { 
    if (host.isEmpty() || dbName.isEmpty() || user.isEmpty() || pass.isEmpty() || port.isEmpty()) { 
     try { 
      throw new SQLException("Database credentials missing"); 
     } catch (SQLException e) { 
      e.printStackTrace(); 
     } 
    } 

    try { 
     Class.forName("org.postgresql.Driver"); 
    } catch (ClassNotFoundException e) { 
     e.printStackTrace(); 
    } 

    try { 
     this.conn = DriverManager.getConnection(this.host + ':' + this.port + '/' + this.dbName, this.user, this.pass); 
    } catch (SQLException e) { 
     e.printStackTrace(); 
    } 

    return true; 
} 

接收類:

_store.execute(); 
boolean result =_store.get(); 

希望我t會有所幫助。

相關問題