1. 程式人生 > >定時器的幾種實現方案

定時器的幾種實現方案

在Android的專案開發過程中,我們經常會用到定時計時功能,本文今天大題整理下這方面的知識技術。聊做總結。

方案一、Timer+TimerTask實現:
這個方案相比無聊時Java開發者還是Android開發者,都是熟悉得不能再熟悉了。不多說,簡單的幾行程式碼做介紹就行:

Timer timer = new Timer();
timer.schedule(timerTask, 10, 3);

TimerTask timerTask = new TimerTask() {
    @Override
    public void run() {
        // TODO:
    }
};

不過這個方案,在Android中使用的時候要注意一下場景下的異常,關於場景介紹以及解決方案見這裡《Timer+TimerTask異常》不再累述
方案二、Handler+Runnable實現:

Handler mHandler = new Handler();
mHandler.postDelayed(runnable, 10 * 1000);
Runnable runnable = new Runnable() {
	@Override
	public void run() {
		//TODO:延時要乾的其他事情
		//迴圈定時最關鍵的一行程式碼:前面呼叫mHandler.postDelayed後,程式開始延時操作,執行完後,又在這裡呼叫了自己給自己發一條延時訊息這樣線上程裡面就形成一個迴圈(死迴圈)
		mHandler.postDelayed(runnable, 10 * 1000);
	}
};

在需要的地方執行下面的程式碼,取消定時迴圈的持續進行:

mHandler.removeCallbacks(runnable);

方案三、RxJava2框架下的Timer功能:
這個方案使用起來超方便,加上RxJava2現在本身火的一塌糊塗,所以使用這個方案,開發的逼格瞬間爆棚,牛逼得不要不要的。

Observable.timer(4, TimeUnit.SECONDS)
            .subscribeOn(Schedulers.io())
            .unsubscribeOn(Schedulers.io())
            .observeOn(AndroidSchedulers.mainThread())
            .subscribe(new Consumer<Long>() {
                @Override
                public void accept(Long aLong) throws Exception {
                    // TODO:
                }
            });

方案四、Timer+TimerTask組合的升級版ScheduledExecutorService:超級好使,不信你看:

ScheduledExecutorService executorService01 = new ScheduledThreadPoolExecutor(2);
// schedule方法排程的任務在delay時長的延遲後只執行一次。
executorService01.schedule(runnable , 3, java.util.concurrent.TimeUnit.SECONDS);

ScheduledExecutorService executorService02 = new ScheduledThreadPoolExecutor(3);
// scheduleAtFixedRate:該方法在initialDelay時長後第一次執行任務,以後每隔period時長,再次執行任務。
// 注意,period是從任務開始執行算起的。開始執行任務後,定時器每隔period時長檢查該任務是否完成,
// 如果完成則再次啟動任務,否則等該任務結束後才再次啟動任務。
executorService02.scheduleAtFixedRate(runnable , 3, 3, TimeUnit.SECONDS);

ScheduledExecutorService executorService03 = new ScheduledThreadPoolExecutor(3);
// 該方法在initialDelay時長後第一次執行任務,以後每當任務執行完成後,等待delay時長,再次執行任務。
executorService03.scheduleWithFixedDelay(runnable , 3, 3, TimeUnit.SECONDS);

ScheduledExecutorService executorService04 = new ScheduledThreadPoolExecutor(3);
executorService04.execute(runnable );

Runnable runnable = new Runnable() {
    @Override
    public void run() {
       // TODO:
    }
};

然後在需要的地方銷燬executorService,避免記憶體洩漏。

    executorService01.shutdown();
    executorService02.shutdown();
    executorService03.shutdown();
    executorService04.shutdown();

使用起來是不是超簡單?

好了,先總結到這裡了。