2

例如,如果我們考慮下面的代碼片段:爲什麼Asynctask或Runnable的生命週期與Activity的生命週期不同?

public class HandlerExample extends AppCompatActivity { 

    private Handler mLeakyHandler = new Handler(); 
    private TextView myTextBox; 

    @Override 
    protected void onCreate(@Nullable Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.activity_samples); 
     myTextBox = (TextView) findViewById(R.id.tv_handler); 

     // Post a message and delay its execution for 10 seconds. 
     mLeakyHandler.postDelayed(new Runnable() { 
      @Override 
      public void run() { 
       myTextBox.setText("Done"); 
      } 
     }, 1000 * 10); 
    } 
} 

Activity被摧毀,無論是配置更改或其它原因,Runnable不會。 Asynctask也是如此。

我的問題是,什麼使它不被破壞,即使它在Activity中聲明?

想想我正在問爲什麼。

+0

如果你不使用線程和活動週期混亂,裝載機是ü最佳選擇。 https://developer.android.com/guide/components/loaders.html – uguboz

+0

其不同,因爲它們不是一個活動。 – petey

回答

2

由於活動類上UI線程上運行可運行的AsyncTask等上後臺線程是從UI線程獨立運行。結束活動不會結束其他線程,除非您專門指示它這樣做。

Runnable描述:

可運行接口應該由任何類,其 實例是旨在由螺紋被執行來實現。

AsyncTask說明:

的AsyncTask能夠正確且容易使用的UI線程。 此類 允許您執行後臺操作 s並在 UI線程上發佈結果,而無需操縱線程和/或處理程序。

並且您還可以通過閱讀文檔來了解有關Threads的更多信息。

+0

處理程序不會在後臺線程上始終運行。它在創建它的線程上運行。對於上面的代碼片段,它在UI線程上創建後會在UI線程上運行。 – HiddenDroid

+0

處理程序在其創建的線程上運行,處理程序只是用於從消息隊列發送和接收的幫助程序對象。銷燬活動也會銷燬處理程序,但不會銷燬在不同線程上運行的runnable。 https://developer.android.com/reference/android/os/Handler.html – V01D1

+0

在線程然後我調用'Runnable.run()'這將運行?我認爲你應該澄清一點,在你的回答中,並且我認爲runnables和其他接口的實現已經從簡單地將它們放入線程 – Elltz

1

什麼使它即使在該活動中聲明也不被銷燬?

new Handler()上調用線程(主線程在你的情況下),Handler與螺紋的Looper的消息隊列相關聯,從所述隊列發送到和處理Runnable S和消息。那些Runnable和消息有一個對目標Handler的引用。即使ActivityonDestroy()方法不是「析構函數」,即當方法返回Activity的實例不會立即死亡(see)時,由於對Activity的隱式引用,存儲器無法進行GC編輯作爲Runnable的外部類別。 Activity將不被延長時間,即直到RunnableLooper的消息隊列中出列並被處理。

參考文獻:

  1. This Handler class should be static or leaks might occur: IncomingHandler
  2. How to Leak a Context: Handlers & Inner Classes