web-dev-qa-db-ja.com

Android:RunOnUiThreadとAsyncTask

Googleは開発者にAsyncTaskの使用を提案していると思います。ただし、パフォーマンスとメモリ効率の点で「新しいスレッド」を使用してから「RunOnUiThread」を呼び出すこととどう違うのかを知りたいと思います。

RunOnUithreadの使用例:

    // some code #1
    Thread t = new Thread("Thread1") {
        @Override
        public void run() {
            // some code #2
            runOnUiThread(new Runnable() {
                public void run() {
                    // some code #3 (that needs to be ran in UI thread)

                }
            });

        }
    };
    t.start();

vs.

AsyncTask:

onPreExecute() {
   // some code #1
}

doInBackground() {
   // some code #2
}

onPostExecute() {
   // some code #3
}

長所/短所は何ですか?

編集:

「コードが見やすい」、「開発者にとって便利」などの答えを探していません。実際に舞台裏で技術的な違いを探しています。

たとえば、以下のポールニコノビッチの答えは、私が見たかった答えだったでしょう。 (ただし、AsyncTaskは同じように動作します)

36
jclova

new Threadを使用すると、実際に実行するたびに新しいスレッドが作成されます。 AsyncTaskただし、最大128スレッドの静的プールを使用し、古いスレッドが存在する場合は常に再利用します。したがって、AsyncTaskをシリアルで10回実行すると、10個のスレッドではなくタスクを10回実行する1つのスレッドのみが作成されます。

それは多くの違いの一つです。

51

基本的に便利です。 AsyncTaskフレームワークはThreadプールの管理を扱い、シンプルで理解しやすいインターフェースを提供します。 UIアクティビティはonPreExecute()onPostExecute()onProgressUpdate()で実行できることはよく知られています(AsyncTaskの使用方法を知っている人は) UIに触れることができないdoInBackground()ですべての「重いリフティング」が行われます。

開発者は、UIスレッドに更新を簡単に投稿し、完了時に結果を返すことができるシンプルなバックグラウンドタスクを簡単に作成できます。それは魔法ではなく、ただの便利さです。

12
Brian Dupuis

主な欠点は、独自のスレッドを使用すると、finishが呼び出されたときにアクティビティが維持されることです。 Androidは、すべてのスレッドが終了するまでのアクティビティ時間を提供します。これにより、アクティビティリークが発生し、最終的にアプリが強制終了されるまでアプリの実行が非常に遅くなります。ユーザーまたはOSのいずれか。

これを確認するには、ADBでプロセスを確認します。アクティビティが終了しても、そこにリソースが占有されているのが見えます。

したがって、独自のスレッドを使用する場合は、必ず管理してください。または、Android api'sを使用します。選択はあなた次第です。

4
Paul Nikonowicz

this によると、AsyncTaskは使いやすいですが、次のような制限があります。

  • コアプールサイズとワークキューは固定です:5プール/ 10要素
    • ハードコーディングされており、変更できません
  • スレッドの優先順位はlowに固定されています
  • 例外処理はThreadほどサポートされていません

また、私が理解していない別の違いがあります。 AsyncTaskの完全なソースコード Androidはオープンソースです:-)

Androidでのコーディングを楽しんでください!

4
Joon Hong

これらは非常に異なっています。

  • 最初に、すべてのユーザーとの対話がメインスレッドで行われ、すべてのグラフィックが機能します。
  • 2番目のAsyncTaskは、ファイルのダウンロードやデータのアップロードなど、短時間の専用アクティビティ用に設計されています。
  • 第三に、すべてのUIとユーザーの対話はメインスレッドで行われるため、このスレッドにデータをプッシュし始めると、デバイスは遅れて表示され、ユーザーのコマンドに対する応答が遅くなります。

UIスレッドで何かを実行する唯一の理由は、ウィジェットと対話するためです。それ以外に、長時間の処理を行う場合は、AsyncTaskを使用します。

編集:

別のスレッドでデータをダウンロードすることもできますが、問題はありません。この問題は、UIを更新するときに発生します。子スレッドからUIを変更することは不可能です。代わりに、UIスレッドに関連付けられたハンドラーを作成するか、UIスレッドで実行する予定の新しいスレッドを作成する必要があります(例のように)。これは退屈なだけでなく、リソースの悲劇的な浪費です。 AsyncTaskは、これを簡単かつ効率的に処理します。

あなたの最後のポイントに対処するには、あなたは正しいです。 AsyncTaskは、pre/postExecuteのメインスレッドにアクセスできます。ただし、タスクが実行している処理(UIラグの主な原因)はそうではありません。タスクを使用すると、タスクが完了するまで待つ必要がなく、タスクや描画したいことは何でも、UIは描画内容に基づいてのみ影響を受けます。

1
ahodder