Androidのメモリの最適化への最も一般的な方法と漏れがOOM要約記事を引き起こし防ぎます

Androidのメモリの最適化への最も一般的な方法と漏れがOOM要約記事を引き起こし防ぎます

序文

メモリ最適化の目的は、効果的に漏れが発生し、当社のアプリケーションメモリの問題を回避する方法の開発に私たちを聞かせすることです。誰もが簡単な下品圏に精通しているメモリリーク、それが解放されるオブジェクトが解放されていないで、リサイクルすることができない一つまたはいくつかの事例で開催されてきたが、もはやGCを生成するために使用しないこと。今、メモリリークや最適化を来て、最初のAndroid用メモリ処理のより直感的かつ包括的に理解され、いくつかの結論を、単純なメモリ割り当てポリシーを見て、その後、漏れやソリューションの一般的な例を引用し、最終的に行う必要があります。

メモリの割り当て

3つのメモリアロケーション戦略、すなわち、静的、スタックとヒープ型のスタイルがあります。メモリ空間を対応する主スタティックメモリ(また、メソッド領域と呼ばれる)、スタック領域とヒープ領域です。次のように:

  • スタティックメモリ領域:静的データ、静的データおよびグローバル定数の主記憶装置。このメモリにプログラムのコンパイル時間が良好で、そこに全体のプログラムの実行時に割り当てられています。 
  • スタック領域:メソッドを実行すると、ローカル変数vivoではスタック上に作成され、これらのメソッドの実装の最後にメモリを開催し、ローカル変数は自動的に解除されます。プロセッサ命令セット、高効率が、割り当てられたメモリの限られた量のスタックメモリ割り当て動作のため。 
  • ヒープ:動的メモリ割り当てとして知られているが、通常は、新たなプログラムがメモリが不足している指揮を指します。このメモリはいないときにJavaのガベージコレクタによって使用されているリサイクルの責任となります。 

スタックとヒープの違い:

(ローカル変数)で定義されたインビボ方法の変数とオブジェクト参照変数のいくつかの基本的なタイプは、スタックメモリ方式で割り当てられます。可変ブロックいくつかの方法を定義する際に、Javaが変数の範囲を超えると、変数も無効である、スタックメモリ空間内の変数に割り当てられ、それに割り当てられたメモリスペースも解放されますオフ、メモリ空間を再利用することができます。ヒープメモリとアレイ(内のすべてのメンバ変数オブジェクトを含む)新しいによって作成されたすべてのオブジェクトを格納するために使用されます。メモリヒープで自動的に管理するためにJavaのガベージコレクタによって割り当てられました。ヒープ・アレイまたはオブジェクトを生成した後、あなたはまた、特別なスタック変数を定義することができ、この可変配列またはオブジェクトの値は、ヒープメモリの先頭アドレスに等しく、この特定の変数は、我々が上記言っ参照変数であります。私たちは、ヒープまたは配列内のオブジェクトにアクセスするには、この参照変数を使用することができます。

例えば:

public class Sample() {

    int s1 = 0;
    Sample mSample1 = new Sample();
    public void method() {
        int s2 = 1;
        Sample mSample2 = new Sample();
    }
}
Sample mSample3 = new Sample();

サンプルS2のローカル変数とクラス変数mSample2参照がスタック上にあるが、mSample2オブジェクトはヒープに存在していると指摘しました。

mSample3はs1とmSample1、およびスタック上に独自のオブジェクト変数のすべてのメンバーを含む、ヒープ上に保存されたオブジェクトの実体を、指摘しました。

概要

基本データ型とスタックに保存されているローカル変数への参照は、参照されるオブジェクトは、スタックエンティティに格納されています。彼らはプロセス変数を属しているため、この方法は、ライフサイクルで終わります。(オブジェクトの実体を引用した基本データ型、および参照を含む)すべてのメンバ変数店・スタック:彼らはクラス、最終的に新しい使用することで、クラスオブジェクトに属しているため。    

メモリ管理

割り当てとオブジェクト空きメモリ管理の問題。

Javaでは、プログラマは、(基本型を除く)の各ターゲット・アプリケーションのメモリ空間のための新しいキーワードを必要とする、すべてのオブジェクトは、スペースのヒープ(ヒープ)の割り当てです。また、オブジェクトの解放が決定され、GCによって実行されます。Javaでは、メモリ割り当てをプログラムによって行われ、メモリが完了するまでにGCから解放され、この方法は、収入と支出がプログラマの仕事を簡素化しません。しかし同時に、それはまた、JVMの仕事を増加させました。これは、Javaプログラムが理由の一つに遅い実行されます。、GCが適切にオブジェクトを解放するためには、GCは、アプリケーション等のオブジェクト、参照、参照、代入を含め、各オブジェクトの動作状態を監視する必要があるため、GCを監視する必要があります。より正確かつタイムリーにオブジェクトを解放するために、オブジェクトの状態を監視し、原則の基礎となるオブジェクトを解放すると、オブジェクトがもはや参照されていることではありません。

メモリリーク

第二に、これらのオブジェクトは役に立たない、即ち、プログラム、メモリリークをいくつかのオブジェクトが割り当てられ、これらのオブジェクトは最初、これらのオブジェクトが、すなわち図中、本通路であり、それに接続することができ、到達可能であり、次の二つの特性を有していますこれらのオブジェクトを使用していました。オブジェクトは、これら2つの条件を満たすことであるならば、これらのオブジェクトは、Javaでのメモリリークと判断することができ、これらのオブジェクトは、GCを回復することはないだろうが、それはメモリを占有しません。

メモリリークのC ++では、より広範な数。一部のオブジェクトは、C ++は、GCがないので、メモリは常に検索されます、届かない、メモリ空間が割り当てられています。Javaでは、これらの到達不能オブジェクトのリサイクルを担当するGCによって、プログラマがメモリリークのこの部分を考慮する必要はありませんように。

分析を通じて、我々は、C ++のために、プログラマはエッジと頂点を管理する必要がある、ということを知っている、とJavaプログラマのためだけのエッジ(頂点のリリースを管理する必要はありません)を管理する必要があります。このように、Javaはプログラミングの効率を改善します。

したがって、上記の分析によって、我々は、Javaで、メモリリークを有しているが、C ++の数より少ない程度にすることを知っています。保証からJava言語なので、任意のオブジェクトが到達可能であり、GC管理により、すべての到達不能オブジェクト。

プログラマのために、GCは目に見えない、実質的に透明です。私たちは、たとえば、GCにアクセスできる唯一のいくつかの関数がありますが、機能にSystem.gc GC()を実行しますが、Java言語仕様に応じて実行されるJVMのガベージコレクタを保証するものではありません関数が定義されています。異なるJVM実装は異なるアルゴリズム管理GCを使用する場合がありますので。GCの一般的に、優先順位の低いスレッド。JVM GC戦略は、多くがある呼び出して、いくつかのメモリ使用量がある程度に達すると、GCが動作し始め、定期的な実装がありますが、いくつかの穏やかはGC、いくつかの割り込み実行形式のGCを実行します。しかし、一般的に言えば、我々は気にしないでください。いくつかの特定の場合を除き、GCのアプリケーションの実装のパフォーマンスへの影響は、例えば、ネットワークゲームなどのWebベースのリアルタイムシステムは、ユーザーがアプリケーションの実行とガベージコレクションのGC突然の中断をしたくない、我々はGCのパラメータを調整する必要があります非常に小さい一連のステップに、例えば、GC穏やかな方法でガベージコレクションをメモリを解放することができ、HotSpotのJVM Sunはこの機能をサポートすることを申し出ました。

Javaのメモリリークの典型的な例:

Vector v = new Vector(10);
for (int i = 1; i < 100; i++) {
    Object o = new Object();
    v.add(o);
    o = null;   
}

この例では、我々は唯一の基準自体は、次いでベクターは依然としてオブジェクトを参照解放場合、ベクトルにオブジェクトのオブジェクト、およびアプリケーションのオブジェクトを循環させるために適用するので、GCの目的は、非リサイクル可能です。Vectorオブジェクトがnullに設定されているオブジェクトがベクトルに追加された場合そのため、あなたはまた、ベクターから削除する必要があり、最も簡単な方法はあります。

一般的なメモリリーク(Benpianフォーカス)

1、漏れコレクションクラス

クラスは、対応するクリアランスメカニズムなしで、要素を追加する唯一の方法(そのようなクラスの静的変数や静的または最終参照され、それを指すグローバルマップなど)グローバル変数の集合である場合には、それだけで上昇し、メモリを占有します、メモリリークが生じます。たとえば、私たちは通常、キャッシュ使用HashMapのようないくつかのことを行う、このような状況では、適切な削除の仕組みを作り、デザート滞在することです。

2 ####、漏れによる単一ケース
による静的シングルトンには、メモリリークが発生する可能性がある、などのアプリケーションのライフサイクルのライフサイクルとなります。

典型的な例

public class AppManager {
    private static AppManager instance;
    private Context context; 

    private AppManager(Context context) {
           this.context = context;
    }

    public static AppManager getInstance(Context context) {
      if (instance != null) {
          instance = new AppManager(context);
      }
      return instance;
    }
}

これは、コンテキストを渡す必要があるため、この単一の例を作成し、それはこのコンテキストのライフサイクルの長さに不可欠であるとき、通常のシングルトンです。

1:アプリケーションのライフサイクルは、アプリケーション全体のライフサイクルであるので、これは何の問題もありませんので、この時点では、アプリケーション・コンテキストに渡された場合。

2:この時点でアクティビティーコンテキストが渡された場合、ターゲットコンテキスト参考例のシートので、対応するアクティビティーコンテキスト出口が、保持された場合、そのライフサイクルは、アプリケーションのライフサイクル全体に等しいので、現在出口活動ときに、メモリリークをもたらした、回復されることはありません

静的インスタンスによって引き起こされるメモリリークを作成するために、図3に示すように、非静的内部クラス 

時々、私たちは同じデータリソースを再作成を避けるために、頻繁に活動を開始する可能性があります、このようなアプローチは、表示されることがあります。 

public class MainActivity extends AppCompatActivity { 
       private static TestResource mResource = null; 
       @Override 
       protected void onCreate(Bundle savedInstanceState) { 
      super.onCreate(savedInstanceState); 
      setContentView(R.layout.activity_main); 
      if(mManager == null){ 
         mManager = new TestResource(); 
      } 
       } 
       class TestResource { 
       //… 
       } 
}

シングルトンTestResourceに非static内部クラスを作成するには、この内部の活動は、回避重複リソースが作成されたもののので、毎回の活動開始データシングルトンを使用するが、そのようなアプローチが、それはメモリリークが発生します、なぜならます非静的内部クラスは限り静的インスタンスにつながっているアプリケーションとインスタンスのライフサイクルは、保持するように、非静的内部クラスながら、外部のデフォルトのクラスへの参照を保持し、静的インスタンスを作成します。アクティビティの参照は、メモリリソースへの活動のリードを適切にリサイクルすることができません。

正しいアプローチがある:内部クラスは、単一のパッケージの実施形態に裏返し静的内部クラスまたはクラスを抽出するために必要であれば、上記の推奨に従って、アプリケーション・コンテキストを使用するコンテキスト。もちろん、コンテキストのアプリケーションは万能薬ではない、次のように、それだけで無差別に、あなたは、アプリケーションのために、3つのシナリオの活動のサービス、コンテキストをコンテキストアクティビティを使用する必要がありますいくつかの場所のためのものではないことができます。アプリケーションとサービスが活動を開始することができますが、それは必要新しいタスクのタスクキューを作成します。そして、ダイアログのために、それだけの活動で作成することができます。

4、匿名の内部クラスのスレッドの非同期の原因がリーク

あなたは匿名クラスを使用して、非同期のスレッドは、その後、気をつけて保持している場合は、この時点で、アクティビティ/フラグメント/ビューを達成するために、後続の際に、何の対策は開示につながりません。
栗の場合: 

public class MainActivity extends Activity { 
  ...{
    Runnable re1 = new MyRunable(); 
    Runnable re2 = new Runnable() { 
    @Override 
    public void run() { 
    } 
     }; 
}

RE1とRE2の違いは、匿名内部クラスの使用RE2、です。これら二つの基準メモリを実行すると、RE1何も特別な、見ることができます。

しかし、1つの以上の引用の内部で、この目標ref2の匿名クラスを達成するために:この$ 0この基準点MainActivity.this。

すなわち、この基準は、次に、非同期スレッドを渡す場合RE2、保持されている現在のMainActivityインスタンスであり、このスレッドは、アクティビティのリークを引き起こし、このAcitivityライフサイクルタイム矛盾しています。

メモリリークによって引き起こさ5、ハンドラ

メインスレッドで操作を消費することなくANRハンドラを回避するために、ネットワークを処理するためのタスクは、コールバック番号などのようなカプセル化されたAPIを要求します。私たちは、ハンドラは、Messageメッセージキューメッセージハンドラて送信を処理した後、メッセージハンドラオブジェクトに送信されていない場合には、一緒に相互に及びますが、メモリリークによって引き起こされたスレッドのメッセージキューを保持することがわかっています。 
ハンドラは、変数(ローカルストレージをスレッド)TLSに属しているため、ライフサイクルと活動が矛盾しています。したがって、この実装はアクティビティ・ビューやライフサイクルとの整合性を確保することは一般に困難である、それは簡単に適切に解放しないにつながることができます。 

知識:Javaで、非static内部クラスと匿名クラスは、それらが属する外部クラスへの潜在的な言及しています。しかし、静的な内部クラスにはありません。

例を見続けました。

public class SampleActivity extends Activity {

  private final Handler mHandler = new Handler() {
    @Override
    public void handleMessage(Message msg) {
      // ...
    }
  }

  @Override
  protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

    // Post a message and delay its execution for 10 minutes.
    mHandler.postDelayed(new Runnable() {
      @Override
      public void run() { ... }}, 1000 * 60 * 10);

    // Go back to the previous Activity.
    finish();
  }
}

分析:
アクティビティの終了(フィニッシュ)は、メッセージが処理される前に遅延がある場合には、10分間のメインスレッドのメッセージキューに残ります。上記引用ハンドラ、およびハンドラを保持し、その外側のクラスへの基準電位(活性)を保持しているから、また、このメッセージを見ることができます。メッセージが処理されるまで、この参照関係は、それによってアプリケーションの漏れを生じる、acitivtyガベージ収集することができる予防、残ります。また、クラス外で開催された非静的な匿名のRunnable同じクラス、漏れにつながります。二つの理由の概要:

要約:

  • 限り、未処理のメッセージがあるように、メッセージがハンドラを引用され、ハンドラは、非静的外部カテゴリへの参照、すなわちアクティビティは、アクティビティにつながる漏れ、その結果、リサイクルすることができないであろう。
  • Runnableをクラスは非static匿名クラスである、それはまた、外部クラスを参照します。

ソリューション:

  • 私たちは、別のクラスファイルにクラスをハンドラや漏れを回避することができ、静的な内部クラスを使用することができます。あなたが外でどこハンドラクラスの活動の中に呼び出したい場合は団結はメモリリークが発生しないように加えて、あなたは、ハンドラ内での活動場所を指し示す弱い参照を使用することができます。
  • Runnableを匿名クラスの場合、それはまた、静的クラスに設定することができます。静的匿名クラスは、外部クラスへの参照を保持していないので。

ソースを見て:

public class SampleActivity extends Activity {

  private static class MyHandler extends Handler {
    private final WeakReference<SampleActivity> mActivity;

    public MyHandler(SampleActivity activity) {
      mActivity = new WeakReference<SampleActivity>(activity);   //弱引用
    }

    @Override
    public void handleMessage(Message msg) {
      SampleActivity activity = mActivity.get();
      if (activity != null) {
        // ...
      }
    }
  }

  private final MyHandler mHandler = new MyHandler(this);

  private static final Runnable sRunnable = new Runnable() { //静态匿名类
      @Override
      public void run() { /* ... */ }
  };

  @Override
  protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

    // Post a message and delay its execution for 10 minutes.
    mHandler.postDelayed(sRunnable, 1000 * 60 * 10);

    // Go back to the previous Activity.
    finish();
  }
}

内部クラスのインスタンスのライフサイクルは長く活動よりも、我々は非静的内部クラスを使用しない場合。最善のアプローチは、その後の活動が配置されて指すように弱参照内のクラスを使用して、静的な内部クラスを使用することです。お勧めの静的内部クラス+弱い参照この方法の概要。各使用前に空の宣告に注意してください。

知識ポイント:

私は簡単なスピーチいくつかのJavaオブジェクトの参照型であるので、ここでは、以前の弱い参照を述べました。

Javaは強い(強い参照)分類参照、ソフト(SoftReference)、弱い(弱い参照)、仮想PhatomReference 4を有しています。

オブジェクトの大規模かつ長期のライフサイクルのためのいくつかのメモリに対処する上で、メモリのオーバーフローを防ぐために、Androidアプリケーションを開発するには、あなたは柔らかく、弱い参照の技術を使用しようとすることができます。

参照されたオブジェクトがガベージコレクトされるソフト参照は、Java仮想マシンに関連付けられたキューを引用し、このソフト参照に追加される場合はソフト/弱参照と参照コホートは(ReferenceQueue)は、組み合わせて使用​​することができます。これにより、バッファとして期限切れソフト/弱参照を除去し、ソフト/弱参照を再利用することができるキュー・オブジェクトのリストを使用して。

デフォルトの画像を大量に使用します私たちのアプリケーションは、そのようなアプリケーションは、デフォルトのアバターを持っていると仮定し、デフォルトのゲームのアイコンは、等が挙げられる。これらの画像は、多くの場所で使用されます。写真を読み込むたび場合は、必要なハードウェア動作するので、ファイルを読み、遅くなり、パフォーマンスの低下につながります。あなたがメモリから直接読み取る必要があるときしたがって、我々は、画像がキャッシュされて検討してください。しかし、画像はメモリスペースを取ることは比較的大きく、画像のキャッシュロットが大量のメモリを必要とし、それがOutOfMemoryを例外になりやすいかもしれません。この時点で、我々はこの問題を回避するために、ソフト/弱参照技術の使用を考慮することができます。以下では、高速バッファのプロトタイプです:まず、HashMapを定義するソフト参照オブジェクト--private地図を保存します。

6、静的メンバ変数を使用して回避しよう

メンバ変数をstaticとして宣言されている場合は、我々はすべてのライフサイクルは、アプリケーションプロセスのライフサイクル全体で同じになります知っています。 

アプリがバックグラウンドにカットアプリは、このメモリは解放されません場合でも、常駐メモリを処理するように設計された場合、これは、一連の問題を引き起こす可能性があります。このアプリは維持しなかった場合、現在の携帯電話のアプリのメモリ管理によると、大きなバックグラウンド・プロセスは、回復を優先させて頂きますため、メモリが占​​め、頻繁に発生する可能性があります生きている相互プロセスはバックグラウンドでアプリを再起動してください。夜間の電話の受話器をインストールした後、アプリの開発に参加すると、電源が空に消費され、フローは、アプリのユーザーは、アンロードまたは沈黙する必要があります。 

修理方法:

  • 最初のクラスの静的メンバを初期化しないでください。これは、遅延初期化とみなすことができます。

7、漏れAsyncTaskによって引き起こされたオブジェクト

AsyncTaskは、特別な注意が必要です。その原則と漏れた以前のハンドラ、スレッドは、原則として、そのライフサイクルと活動は必ずしも同じではありませんが、似ている漏れました。

 ソリューション:アクティビティ出口、バックグラウンドタスクのAsyncTaskの終了。

 しかし、問題は、終了する方法ですか?

 公共の最終ブールキャンセル(ブールmayInterruptIfRunning):AsyncTaskは、対応するAPIを提供します。

その説明は、読み取ります。

// Attempts to cancel execution of this task. This attempt will fail if the task has already completed, already been cancelled, or could not be cancelled for some other reason.
// If successful, and this task has not started when cancel is called, this task should never run. If the task has already started, then the mayInterruptIfRunning parameter determines whether the thread executing this task should be interrupted in an attempt to stop the task.

キャンセルは、あなたが実行している場合、それがバックグラウンドタスクを中断することが、必ずしも成功していません。これは私がそれを飛んでいないと言ってどのように感じるのですか?

はい、それは飛んでいません。

だから、どのようにそれのポイントを飛ぶことができますか?私たちは、公式の例を見て:

private class DownloadFilesTask extends AsyncTask<URL, Integer, Long> {
     protected Long doInBackground(URL... urls) {
         int count = urls.length;
         long totalSize = 0;
         for (int i = 0; i < count; i++) {
             totalSize += Downloader.downloadFile(urls[i]);
             publishProgress((int) ((i / (float) count) * 100));
             // Escape early if cancel() is called
             // 注意下面这行,如果检测到cancel,则及时退出
             if (isCancelled()) break;
         }
         return totalSize;
     }

     protected void onProgressUpdate(Integer... progress) {
         setProgressPercent(progress[0]);
     }

     protected void onPostExecute(Long result) {
         showDialog("Downloaded " + result + " bytes");
     }
 }

公式には終了を防ぐことはできませんでした、バックグラウンドのサイクルタイムで状態を解除聴き、良い例です。

あなたを思い出させるために、意図的にグーグルの説明AsyncTaskで英語の大部分を下に置きます:

// AsyncTask is designed to be a helper class around Thread and Handler and does not constitute a generic threading framework. AsyncTasks should ideally be used for short operations (a few seconds at the most.) If you need to keep threads running for long periods of time, it is highly recommended you use the various APIs provided by the java.util.concurrent pacakge such as Executor, ThreadPoolExecutor and FutureTask.

私の同情中国の広大な領土、広大な土地、不足している何が、敏感な読書英語の欠如です。

AsyncTask数秒まで、短い時間のかかる操作に適しています。あなたが長い時間のかかる操作をしたい場合は、そのようなエグゼキュータ、ThreadPoolExecutorとFutureTaskなど、他のjava.util.concurrentのパッケージの下にAPIを使用しています。

ピットステッピング避けるために、英語を学びます!

8、BroadcastReceiverオブジェクト

様々な理由は、()メソッドの登録を解除するために呼び出すことはありませんでした。

解決策はつまり、簡単であり、()メソッドの登録を解除するために呼び出してください。

ちなみに、私は時にプロンプ​​トレシーバ・オブジェクトがregisterReceiver()成功(なしの呼び出しには)、エラーの登録を解除しない、仕事では逆の状況に会いました:

// java.lang.IllegalArgumentException: Receiver not registered ...

ソリューション:

スキームA:registerReceiverで(後)が登録解除()FLAGかどうかを決定するフラグを提供しました。私はこのバグに遭遇しましたが、ほとんどすべてのように書かれた記事のためにウェブを検索し、解決策はそう常にあります。しかし、このコードは少し醜いことは否めません。

オプション2:私は、後に、ダニエルリマインダーを耳Androidのソースコードで、より一般的な文言を見ました:

// just sample, 可以写入工具类
// 第一眼我看到这段代码,靠,太粗暴了,但是回头一想,要的就是这么简单粗暴,不要把一些简单的东西搞的那么复杂。
private void unregisterReceiverSafe(BroadcastReceiver receiver) {
    try {
        getContext().unregisterReceiver(receiver);
    } catch (IllegalArgumentException e) {
        // ignore
    }
}

図9に示すように、オブジェクトへのビットマップによるリーク

Bitmapオブジェクトは、リソースへの直接または間接の参照を、それが割り当てヌルでメソッドを呼び出すリサイクル空にするのに最適な時間はありませんが、いくつかは、ああ呼び出していない多くの場所内部のアンドロイドのソースを言うの?

はい、私はそれを呼び出すされていない場合、ビットマップのみの方法を確定実行したときに、JavaのGCに頼る呼び出すことができ、最高であると言うためにここにいます、

リソースを解放するためにnavtive nativeDestructorを()を実行するこの方法は、実際には、それは、削除ビットマップで、その機能を見てみましょう。

概要

1.活動と他の構成要素への参照は、アクティビティのライフサイクル内で制御されなければならない、そうでない場合、getApplicationContext又はgetApplication、長官基準リーク外活動のライフサイクルを避けるためにあるオブジェクトの使用を検討してください。 

2.外部のメンバ変数が家空を検討するためにタイムリーにも使用したい場合でも、静的変数や静的な内部クラスで(コンテキストを含む)外部の非静的メンバ変数を使用しないようにしてください、しかし、あなたはまた、外部を参照するためにクラス内で弱参照を使用することができます変数クラス。 

内部アクティビティクラスのオブジェクトよりも長いライフサイクルの3、及び外部のクラスで使用される内部メンバー変数クラス、内部クラスは、静的内部クラス、外部基準部材変数クラスへの弱参照を使用して、静的な内部クラスに変更することができます。

4.Handlerは、オブジェクトへの参照が弱参照を使用するのが最善である保持されているリソースが解放されたとき、ハンドラはまた、内部のメッセージをフラッシュします。例えば、活性のonStopまたはonDestroyは、Runnableを、およびメッセージハンドラオブジェクトをキャンセルします。

Java実装5.、またオブジェクトを検討すべきリリースは、最良の方法である、使用しないときオブジェクトに、明示的にこのターゲットがnullの場合、最初の呼び出しのビットマップは、このようなリサイクルを()を使用して終了し、その後、割り当てそれはリリースを作成するの原則に従うことが最善である、など; Fuがnullの場合、空の配列が直接絵や他のリソースまたは間接参照への参照(配列= nullを使用array.clearを())があります。  

6.資源BraodcastReceiverの使用の使用のために、ContentObserverを適切なリソースを閉じ、ファイル、カーソルカーソル、ストリーム、ビットマップなど、活動が破壊されたときに速やかにシャットダウンまたはログオフする必要があります。 

オブジェクトのライフサイクル、単一の実施形態に特別な注意は、そのようなグローバルなライフサイクルのセットとして静的オブジェクトに敏感7。

あなたは記事がよく書かれていると思われる場合さて、ここで終了する記事は、賞賛の聖歌を与えますか?あなたが改善することが必要と思われる場合は、私にメッセージをお願いします。深刻なお問い合わせ、補正不足になります。ありがとうございます。

おすすめ

転載: blog.51cto.com/14332859/2444741