### new vs newInstance() 我們有一個 Class 叫 MyFragment.java,內容如下 : ```java /** * my fragment */ public class MyFragment extends Fragment { public static MyFragment newInstance() { return new MyFragment(); } } ``` 我們可以通過下面的代碼來生成 MyFragment 的 Object : ```java // create fragment using new Fragment f1 = new MyFragment(); // create fragment using static method Fragment f2 = MyFragment.newInstance(); ``` 接觸過 Android Programming 的朋友都會見過上面兩種方法,那一種才是正確的方法呢 ? ### Android 的生命週期 上面的答案和 Android 的生命週期有極大的關係,因為 Android 會把不在面前 (顯示中) 的 Fragment Recycle 掉,然後在 Fragment 再出現 (例如使用者按了 Back 制) 時重新建立。這時,Android 是會使用 new Fragment() 的方法建立新的 Fragment 重新顯示。 ### 產生問題 如果 Fragment 是沒有參數的話,是沒有任何問題的,像上面的 MyFragment 一樣。我們改寫一下 MyFragment 的內容,讓它可以接收參數 : ```java /** * my fragment */ public class MyFragment extends Fragment { private int id; public static MyFragment newInstance() { return new MyFragment(); } public MyFragment() { super(); } public MyFragment(int id) { super(); this.id = id; } } ``` 有了新的 Constructor 後,我們可以在 `new MyFragment()` 時傳入 id 參數了 ! ```java // create fragment with arguments Fragment f1 = new MyFragment(1); ``` 這樣很完美 ! 但是我們忘記了 Android 可是會因為節省記憶體而把 Fragment 斬掉,然後需要再顯示時以 new Fragment() 重新建立,那我們傳入的 id 不就會一同被斬掉了嗎 ? 答案是對的,id 會隨著 Fragment 斬掉而一同遠去 ... ### 解決方法 如果有看過另一篇文章講解過 [Android 為 Fragment 傳入參數](https://cdn.19site.net/posts/118)的朋友,會知道我們可以使用 Bundle 來為 Fragment 傳入參數 ! Bundle 不會因為 Fragment 的斬掉而清走,當 Android 重新建立 Fragment 時,先前的 Bundle 會重新連接上,故可以使用 `getArguments()` 取得 Bundle 物件進行設定動作。而 newInstance 的作用就是為了把傳入到 Fragment 的參數規範起來。 我們再把上面的 `MyFragment.java` 改寫一下 : ```java /** * my fragment */ public class MyFragment extends Fragment { private int id; public static MyFragment newInstance(int id) { Bundle bundle = new Bundle(); bundle.putInt("id", id); MyFragment fragment = new MyFragment() fragment.setArguments(bundle); return fragment ; } } ``` 使用這樣的方法來傳入參數,就可以確保 Fragment 重新建立時不會有缺失了 ! ```java // create fragment with arguments Fragment f1 = MyFragment.newInstance(1); ``` 官方說明文件 https://developer.android.com/reference/android/app/Fragment.html#Fragment()