2012-06-01 112 views
106

我正在開發android應用程序一段時間,並且關注了很多關於活動生命週期和應用程序生命週期的文章。Activity.finish()方法在做什麼?

我知道Activity.finish()方法調用的方式Activity.onDestroy(),也從堆棧中刪除活動,我想它指向操作系統和垃圾回收器,他可以「做他的竅門」,並釋放內存時發現它是一個很好的時間這樣做...

我來到這個職位 - Is quitting an application frowned upon?並閱讀馬克墨菲的答案。

這讓我對finish()方法實際做了什麼感到困惑。

有沒有機會打電話給finish()onDestroy()不會被叫?

回答

119

當調用上的活動finish()onDestroy()執行這種方法可以做這樣的事情的方法:

  1. 辭退任何對話框中的酶活性管理。
  2. 關閉活動管理的所有遊標。
  3. 關閉所有打開的搜索對話框

此外,onDestroy()不是析構函數。它實際上並沒有破壞對象。這只是一種基於特定狀態而調用的方法。因此,在超類的onDestroy()運行並返回後,您的實例仍然存活並且非常好.Android會一直保留進程以防用戶想要重新啓動應用程序,這會使啓動階段更快。這個過程不會做任何事情,如果內存需要回收,這個過程將被終止。

+4

so finish()method只觸發onDestroy()的調用,就是這樣? –

+0

是的,它觸發onDestroy()將破壞活動的概念活動是生命週期 –

+0

所以在完成後(),這個活動中的所有變量將被銷燬,對吧?當我再次回到這個活動時,它們將被重新宣佈或初始化,對吧? –

12

onDestroy()是爲了最終清理 - 釋放資源,你可以自己,關閉開放連接,讀者,作家等。如果你不覆蓋它,系統就會做它所要做的。

另一方面,finish()只是讓系統知道程序員想要當前Activity完成。因此,之後它會調用onDestroy()

一些需要注意的:

這是沒有必要的finish()呼叫觸發到onDestroy()通話。不可以。正如我們所知,如果覺得當前需要釋放的Activity需要的資源,android系統可以自由地殺死活動。

+1

你寫的完成()讓系統知道的通知活動需要完成。所以這就像說「做x =告訴系統做x」。秒的事情:從你的答案,這聽起來像有一種方式,我會叫finish(),系統將決定不調用onDestroy()?可能嗎? –

+0

你有正確的第一部分。調用'finish()'告訴系統完成'活動'。 do語句中的「x」部分是「完成(銷燬)'Activity'」。第二部分是錯誤的。其實,我在那裏錯過了一個字。我編輯了答案。 'onDestroy()'不僅僅由'finish()'觸發,系統也可以自己調用它。 –

+1

我剛剛讀了你的答案。現在我已經投票選出了答案,因爲我發現你的解釋很有意思,但是我希望看到其他人在將其標記爲「答案」之前是否還有別的話要說。現在感謝:) –

5

Finish()方法將銷燬當前活動。 如果您不希望此活動在用戶按下後退按鈕時一次又一次加載,則可以使用此方法。 基本上它從當前堆棧清除活動。

-5

完成()剛剛發回給在Android上以前的活動,也可以是你可以說,這是前進了一大步應用

2

@ user3282164按照Activity生命週期過程應該onPause() - >onStop() - >onDestroy()致電finish()

該圖不顯示由系統引起的[活動正在運行]到[onDestroy()]的任何直線路徑。

醫生說 「注意,此方法可永遠被調用,在低內存情況下的系統沒有足夠的內存,讓您的活動的過程中它的onPause之後運行()方法被調用。

+0

**不正確**請參閱:http://stackoverflow.com/questions/12655898/finish-and-the-activity-lifecycle/30227647#30227647 – ceph3us

3

各種答案和筆記聲稱finish()可以跳過onPause()和onStop()並直接執行onDestroy()。公平地說,Android文檔(http://developer.android.com/reference/android/app/Activity.html)記錄了「活動正在完成或被系統銷燬」,這很不明確,但可能表明finish()可以跳轉到onDestroy()。

完成()上的JavaDoc同樣令人失望(http://developer.android.com/reference/android/app/Activity.html#finish()),實際上並沒有注意到響應finish()時調用了什麼方法。

因此,我寫了這個迷你應用程序下面記錄每個國家入境時。它包含一個調用finish()的按鈕 - 所以你可以看到哪些方法被觸發的日誌。這個實驗會提示finish()確實也是也調用onPause()和onStop()。這裏是我得到的輸出:

2170-2170/? D/LIFECYCLE_DEMO﹕ INSIDE: onCreate 
2170-2170/? D/LIFECYCLE_DEMO﹕ INSIDE: onStart 
2170-2170/? D/LIFECYCLE_DEMO﹕ INSIDE: onResume 
2170-2170/? D/LIFECYCLE_DEMO﹕ User just clicked button to initiate finish() 
2170-2170/? D/LIFECYCLE_DEMO﹕ INSIDE: onPause 
2170-2170/? D/LIFECYCLE_DEMO﹕ INSIDE: onStop 
2170-2170/? D/LIFECYCLE_DEMO﹕ INSIDE: onDestroy 

package com.mvvg.apps.lifecycle; 

import android.app.Activity; 
import android.os.Bundle; 
import android.util.Log; 
import android.view.View; 
import android.view.View.OnClickListener; 
import android.widget.Button; 
import android.widget.LinearLayout; 
import android.widget.Toast; 

public class AndroidLifecycle extends Activity { 

    private static final String TAG = "LIFECYCLE_DEMO"; 

    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     Log.d(TAG, "INSIDE: onCreate"); 
     setContentView(R.layout.activity_main); 
     LinearLayout layout = (LinearLayout) findViewById(R.id.myId); 
     Button button = new Button(this); 
     button.setOnClickListener(new OnClickListener() { 

      @Override 
      public void onClick(View view) { 
       Toast.makeText(AndroidLifecycle.this, "Initiating finish()", 
         Toast.LENGTH_SHORT).show(); 
       Log.d(TAG, "User just clicked button to initiate finish()"); 
       finish(); 
      } 

     }); 

     layout.addView(button); 
    } 

    @Override 
    protected void onStart() { 
     super.onStart(); 
     Log.d(TAG, "INSIDE: onStart"); 
    } 

    @Override 
    protected void onStop() { 
     super.onStop(); 
     Log.d(TAG, "INSIDE: onStop"); 
    } 

    @Override 
    protected void onDestroy() { 
     super.onDestroy(); 
     Log.d(TAG, "INSIDE: onDestroy"); 
    } 

    @Override 
    protected void onPause() { 
     super.onPause(); 
     Log.d(TAG, "INSIDE: onPause"); 
    } 

    @Override 
    protected void onResume() { 
     super.onResume(); 
     Log.d(TAG, "INSIDE: onResume"); 
    } 

} 
42

我在@K_Anas 2美分答案。 我對finish()方法執行了一個簡單的測試。 上市重要的回調方法在活動週期

  1. 在調用的onCreate(完成()):的onCreate() - >的onDestroy()
  2. 調用完成()的調用onStart():的onCreate() onStart() - > onResume() - > onPause() - > onStop() - > onDestroy()
  3. onResume()調用finish():onStop () - > onDestroy()

我的意思是說當finish()被執行時,這些方法的對應物以及它們之間的任何方法都會被調用。

如:

onCreate() counter part is onDestroy() 
onStart() counter part is onStop() 
onPause() counter part is onResume() 
+0

如果您在onPause中調用finish,該怎麼辦?它會調用onStop> onDestroy? – rmpt

+0

該表格非常實用且具有描述性(您必須向下滾動一下)https://developer.android.com/reference/android/app/Activity.html#ActivityLifecycle – winklerrr

+0

@winklerrr很好。是的,這很有用 – Prakash

1

我的研究表明,finish()方法實際上一些地方銷燬作業在排隊,但活動不會立即銷燬。但破壞計劃。

例如,如果你把finish()onActivityResult()回調,而onResume()尚未運行,那麼首先onResume()將被執行,而onStop()onDestroy()後才被調用。

注意:onDestroy()可能根本不會被調用,如documentation中所述。

0

看來,迄今爲止唯一正確的答案是由romnex給出的:「onDestroy()可能根本不會被調用」。即使在實踐中,在幾乎所有情況下,都不能保證:finish()上的documentation只承諾將活動的結果傳播回調用方,但僅此而已。此外,lifecycle documentation澄清說,只要onStop()完成(或者在較早的設備上更早),操作系統就可以支持該活動,儘管在簡單的測試中不太可能並且因此難以觀察,但可能意味着該活動可能在執行onDestroy()之前或甚至在執行之前被殺死。所以如果你想在調用finish()時確定一些工作已經完成,你不能把它放在onDestroy()中,但是需要在你調用finish()的同一個地方完成,就在實際之前稱它。

1

onCreate()中的調用完成將不會像@prakash所說的那樣直接調用onDestroy()。在您將控制權歸還給Android之前,finish()操作甚至不會開始。在的onCreate(

呼叫結束())的onCreate() - >在onStart() - >的onResume()。如果用戶退出應用程序將調用- >的onPause() - >的onStop() - >的onDestroy()

撥打在onStart完成()()的onCreate() - >在onStart() - >的onStop() - >的onDestroy()

調用完成()在的onResume()的onCreate() - >在onStart() - >的onResume() - >的onPause() - >的onStop() - > onDestroy()

如需進一步參考請查看此oncreate continuous after finish & about finish()

3

此外,如果你調用一個意圖後結束(),你不能再回到以前的活動與「後退」按鈕

startActivity(intent); 
finish(); 
相關問題