Runnable posted in another runnable not executed

戏子无情 提交于 2020-01-24 20:22:04

问题


I'm trying to run a runnable from another runnable using Handler.post() method of my singleton but this second runnable is not being run until after the original runnable finishes. In the example code below I am calling MyManager,getInstance().startCommand() from somewhere in the application. The myRun variable in the MyCommand class has a sleep put on the thread so I can test a timeout feature, but the runnable called mTimeoutTimer is not be executed until AFTER the myRun runnable is finished. Why is this happening, and how can I change that?

public class MyManager{
    private MyManager sInstance;
    private Handler mHandler;
    private Runnable mTimeoutTimer;

    public static MyManager getInstance(){
        if(sInstance == null){
            sInstance = new MyManager();
        }
        return sInstance;
    }

    private MyManager(){
        mHandler = new Handler();
        mTimeoutTimer = new Runnable() {
        @Override
        public void run() {
            Log.e(“RUNNABLE RUNNING!”);
        }
    };

    public class MyCommand {
       private Runnable myRun;

       public MyCommand(){
           myRun = new Runnable() {
               @Override
               public void run() {
                   MyManager.getInstance().startTimeoutTimer();

                   try {
                       Thread.sleep(COMMAND_TIMEOUT_MILLIS * 3);
                   } catch (InterruptedException e) {}

                   MyCommand.this.execute();
               }
           };
       }

       public void execute() {
           myRun.run();
       }
    }


    private void startTimeoutTimer(){
        mHandler.postDelayed(mTimeoutTimer);
    }


    public void startCommand(){
        new MyCommand().execute();
    }
}

回答1:


That is because Handler are called in the Main thread so it will wait for the other one to finished

instead put your other handler in the HandlerThread to run your handler on a separate thread

    HandlerThread thread = new HandlerThread("HandlerThread");
    thread.start();
    Handler handler = new Handler(thread.getLooper());

The documentation of HandlerThread

  Handy class for starting a new thread that has a looper.
  The looper can then be used to create    handler classes. 
  Note that start() must still be called.



回答2:


A single thread cannot execute two Runnables at once (or any two things at once, really).

If you post both to the Handler instances bound to the same thread (generally the UI thread) then one will necessarily have to wait for the other to finish.

To run in another thread, use

new Thread(mTimeoutTimer).start();

Or you can use a thread pool. See the documentation.



来源:https://stackoverflow.com/questions/24172356/runnable-posted-in-another-runnable-not-executed

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!