Androidはメインスレッドとサブスレッドで実行されます.

9114 ワード

//new    HandlerThread
private static final HandlerThread sWorkerThread = new HandlerThread("launcher-loader");
    static {
        sWorkerThread.start();
    }
private static final Handler sWorker = new Handler(sWorkerThread.getLooper());

//      
private void runOnMainThread(Runnable r, int type) {
        if (sWorkerThread.getThreadId() == Process.myTid()) {
            // If we are on the worker thread, post onto the main handler
            mHandler.post(r);
        } else {
            r.run();
        }
    }
//       
public static void runOnWorkerThread(Runnable r) {
      if (sWorkerThread.getThreadId() == Process.myTid()) {
          r.run();
      } else {
          // If we are not on the worker thread, then post to the worker handler
          sWorker.post(r);
      }
    }

新主スレッドのHandlerは、mHandlerだけで現在のrunnableを主スレッドで実行する.postでいいです.例えばuiを更新すれば直接できます.
    public static class PipelineThreadHandler extends Handler }
    mHandlernew PipelineThreadHandler();

システムは同じhandlerを多重化してプライマリスレッドで実行
public class PipelineThread extends Thread {
    private static final String LOG_TAG = "PipelineThread";
    private static final String THREAD_NAME_PREFIX = "Pipeline-";

    private static PipelineThread sInstance;

    private Handler mHandler;

    public PipelineThread() {
        super();
        setName(THREAD_NAME_PREFIX + getName());
    }

    public PipelineThread(String name) {
        super();
        setName(THREAD_NAME_PREFIX + name);
    }

    public void run() {
        try {
            // preparing a looper on current thread
            // the current thread is being detected implicitly
            Looper.prepare();

            // now, the handler will automatically bind to the
            // Looper that is attached to the current thread
            // You don't need to specify the Looper explicitly
            synchronized (this) {
                mHandler = new PipelineThreadHandler();
                this.notifyAll();
            }

            // After the following line the thread will start
            // running the message loop and will not normally
            // exit the loop unless a problem happens or you
            // quit() the looper (see below)
            Looper.loop();
          } catch (Throwable t) {
            Log.e(LOG_TAG, "halted due to an error", t);
          } 
    }


    /**
     * Gets the instance of handler. This method should only be invoked after the Pipeline thread
     * has been started. If this method is invoked before the Pipeline thread has been started, it will throw
     * the PipelineThreadException. 
     * 
     * @return
     */
    public Handler getHandler() 
    throws PipelineThreadException {
        synchronized (this) {
            if (this.getState() == Thread.State.NEW) {
                throw new PipelineThreadException("Pipeline thread " + this.getName() + " not started.");
            }

            if (mHandler == null) {
                try {
                    Log.d(LOG_TAG, "Going to wait for handler to be initialized.");
                    this.wait();
                    Log.d(LOG_TAG, "Wait over. Handler is " + mHandler);
                } catch (InterruptedException e) {
                    Log.e(LOG_TAG, e.getMessage(), e);
                }
            }
        }

        return mHandler;
    }

    public static synchronized final PipelineThread getInstance() {
        if (sInstance == null) {
            sInstance = new PipelineThread();
            sInstance.start();
        }

        return sInstance;
    }

    public static class PipelineThreadHandler extends Handler {

    }
}
//      PipelineThread.getInstance().getHandler()

2つの古典的な比較プライマリスレッドとサブスレッド
handler = new Handler(new Handler.Callback() {  
//....
Thread.currentThread().getId()); //       id        
}


 HandlerThread ht = new HandlerThread("MyThread");  
        ht.start();  
        Log.d(TAG,"=========>" + ht.getId());  //          id       
        handler = new Handler(ht.getLooper(), new Handler.Callback() {  
        //...