ホームへ戻る

5.1 別スレッドで処理をする


 AndroidのUIに関する部分はシングルスレッドで動作することしか許されていません。
試しに別スレッドからUIを操作すると、例外が発生します。
これは、Viewのset系メソッド内に存在する、画面再描画メソッドである invalidate() の中で、
呼び出し元が、UIスレッドかどうか確認しており、別スレッドなら
「Only the original thread that created a view hierarchy can touch its views.」
と例外が吐きだされるためです。

すなわちAndroidアプリ環境では、マルチスレッドで動かしつつも、UIはシングルスレッドのみで動かす仕組みが必要になります。
そこで2種類のスレッドを利用する仕組みが存在しています。

1. 普通のThreadを使う。Android用のHandlerを使って定期的にUIスレッドに仕事を渡す。
2. Android独自のSyncTaskを使う。非同期スレッドから定期的にUIスレッドの関数を呼ばせる。

それでは「1」から紹介します。

まず、最も簡単な書き方で1秒に1度「thread」とログに表示するプログラムを書いてみましょう。


public class AndroidsCastleActivity extends Activity {

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

                (new Thread(new Runnable() {
                        @Override
                        public void run() {
                                while(true){
                                        Log.d("test","thread");
                                        try {
                                                Thread.sleep(1000);
                                        } catch (InterruptedException e) {}
                                }
                        }
                })).start();
        }

}


runメソッドに別スレッドで処理したい内容を書きます。
1000ms待機しては、Logに"thread"を表示するようになっています。

Runnableを実装して呼び出しても良いです。


public class AndroidsCastleActivity extends Activity implements Runnable {

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

                (new Thread(this)).start();
        }

        @Override
        public void run() {
                while(true){
                        Log.d("test","thread");
                        try {
                                Thread.sleep(1000);
                        } catch (InterruptedException e) {}
                }
        }

}


別クラスにしてもOK


public class AndroidsCastleActivity extends Activity {

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

                (new Thread(new myThread())).start();
        }

        class myThread implements Runnable {
                @Override
                public void run() {
                        while (true) {
                                Log.d("test", "thread");
                                try {
                                        Thread.sleep(1000);
                                } catch (InterruptedException e) {}
                        }
                }
        }
}


しかしこれらは別スレッドですから、先ほど述べた通り、UIを扱うことが出来ません。
そこで、Handlerの出番になります。

Handlerの説明は次節で。

→分からないことがあれば掲示板で質問して下さい


Portions of this page are modifications based on work created and shared by Google and used according to terms described in the Creative Commons 3.0 Attribution License.

- Remical Soft -