2015-07-10 74 views
-1

請耐心等待,我是Android開發的初學者。 我想把網址放入一個ArrayList中,並將ArrayList返回給MainActivity。在Asynctask中添加元素後返回ArrayList到MainActivity

我可以在Connection類中更新它,但是當我嘗試檢查它是否在getValidURL()方法中工作時,它不顯示任何內容。

在MainActivity中,我還使用Log.d來記錄返回的ArrayList是否爲空,它是。

我在做什麼錯?我覺得我犯了一個非常愚蠢的錯誤,我不知道它是什麼。

MainActivity.urlEnteredButton():

public void urlEnteredButton(View view) throws IOException { 

    Button ok = (Button) findViewById(R.id.urlButtonOK); 

    Intent displayArticleScreen = new Intent(this, SecondActivity.class); 

    GetURLS work = new GetURLS(); 

    ArrayList<String> URLS = work.getValidURL(); 

    if(URLS.isEmpty()){ 
     Log.d("URL IN MAIN IS: " , "EMPTY!!!!!"); 
    } 
     for(String s : URLS){ 
      Log.d("URL Main: " , s); 
     } 

    if(!URLS.isEmpty()) { 
     String[] workingURLS = URLS.toArray(new String[URLS.size()]); 
     final int result = 1; 

     displayArticleScreen.putExtra("url", workingURLS); 

     startActivity(displayArticleScreen); 
    } 
} 

GetURLS.java

import android.os.AsyncTask; 
import android.util.Log; 
import android.widget.TextView; 

import org.jsoup.Jsoup; 
import org.jsoup.nodes.Document; 
import org.jsoup.nodes.Element; 
import org.jsoup.select.Elements; 

import java.io.IOException; 
import java.util.ArrayList; 

public class GetURLS { 

    ArrayList<String> workingURLS = new ArrayList<String>(); 
    Connection myConnection = new Connection(); 

    public GetURLS() throws IOException { 

     myConnection.execute(); 

    } 

    public void update(ArrayList<String> temp){ 

     for(String s : temp){ 
      workingURLS.add(s); 
     } 

     for(String s : workingURLS){ 
      Log.d("URL in workingURLS", s); 
     } 

    } 

    public ArrayList<String> getValidURL(){ 
     for(String s : workingURLS){ 
      Log.d("URL in getValidURL()", s); 
     } 
     return workingURLS; 

    } 

    private boolean isValidURL(String temp){ 
     if(temp.contains("thestar.com") && temp.length() > 75 && (temp.contains("/news/") || temp.contains("/business/") || temp.contains("/sports/") || temp.contains("/entertainment/") || temp.contains("/life/"))){ 
      return true; 
     } 
     return false; 
    } 

    private class Connection extends AsyncTask<Void , Void, ArrayList<String>> { 

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

     @Override 
     protected ArrayList<String> doInBackground(Void... params){ 
      Document doc = null; 
      Elements links = null; 


      try { 
       doc = Jsoup.connect("http://www.thestar.com/").get(); 
       links = doc.select("a"); 
      } catch (IOException e) { 
       e.printStackTrace(); 
      } 

      if (links != null) { 
       for(Element link : links){ 
        String temp = link.attr("href"); 
        if(isValidURL(temp)){ 
         tempAL.add(temp); 
        } 
       } 
      } 

      return tempAL; 

     } 

     @Override 
     protected void onPostExecute(ArrayList<String> tempAL){ 

      update(tempAL); 

     } 

    } 

} 

在logcat中,我得到了以下信息:

07-10 16:41:58.824 21413-21413/com.bloopbloop.ishyfishyy.thestargrabber D/URL IN MAIN IS:﹕ EMPTY!!!!! 

07-10 16:41:59.894 21413-21413/com.bloopbloop.ishyfishyy.thestargrabber D/URL in workingURLS﹕ http://www.thestar.com/news/crime/2015/07/10/lecent-rosss-mother-too-grief-stricken-to-speak.html 
//followed by all the other URLS I requested 
  • 在MainActivity中,爲什麼if(URLS.isEmpty())根據時間戳在ArrayList<String> URLS = work.getValidURL();之前執行?

  • 爲什麼GetURLS類中的ArrayList不會更新?

在此先感謝

回答

0

由於myConnectiont.execute()正在啓動一個的AsyncTask,它在後臺同時發生。因此即使您所有的網絡電話都沒有完成,執行過程仍在MainActivity中繼續。這就是爲什麼你的日誌顯示你的ArrayList是空的:在執行時,它是空的。只有在聯網的線程完成之後,它們纔會被填充,並調用update()方法。

+0

我必須在啓動Asynctask後讓應用程序暫停的主線程完成,然後繼續? –

+0

雖然你冒着ANR的風險,如果網絡通話失敗,並且當應用程序沒有做任何事情時令用戶感到沮喪,你可以。理想情況下,您可以爲用戶設置某種進度指示器(即使它只是一個微調對話框)。您可能需要考慮在MainActivity和AsyncTask之間實現回調系統,以便MainActivity知道完成情況。你可以看到[這裏](http://stackoverflow.com/questions/9963691/android-asynctask-sending-callbacks-to-ui) – ozymandias