首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> Java 程式設計 >> Java 相關知識

Java Timer 定時器完整指南:從基礎排程到多任務協作控制

     編輯:Java 相關知識

核心類別架構

Java 定時任務核心由兩個類別組成:

  • Timer:排程器,負責管理任務佇列與執行緒調度
  • TimerTask:任務載體,實作 run() 方法定義具體執行邏輯

Timer 兩種核心排程模式

方法特性適用場景
schedule(task, delay, period)固定延遲執行
上次執行結束 → 等待 period → 下次執行
頻率固定、允許執行時間漂移的一般性任務
scheduleAtFixedRate(task, delay, period)固定頻率執行
按理論時間點觸發,若延遲則追趕執行
需精確時間點觸發的任務(如每整點備份)

範例一:基礎單一任務排程

package com.bjpowernode.test;

import java.io.IOException;
import java.util.Timer;

public class TimerTest {
    public static void main(String[] args) {
        Timer timer = new Timer();
        
        // 1秒後啟動,每2秒執行一次
        timer.schedule(new MyTask(), 1000, 2000);
        
        // 主執行緒等待使用者輸入 's' 停止
        System.out.println("輸入 's' 停止定時器...");
        while (true) {
            try {
                int in = System.in.read();
                if (in == 's') {
                    timer.cancel(); // 終止所有任務
                    break;
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

    static class MyTask extends TimerTask {
        @Override
        public void run() {
            System.out.println("________ " + new java.util.Date());
        }
    }
}

執行流程說明

  1. 程式啟動 → 1 秒後首次執行
  2. 印出 "________" + 當前時間
  3. 每隔 2 秒重複執行
  4. 使用者輸入 's' → timer.cancel() → 程式結束

範例二:多任務協作與動態控制

package com.bjpowernode.test;

import java.io.IOException;
import java.util.Date;
import java.util.Timer;

public class TimerTest2 {
    public static void main(String[] args) {
        Timer timer = new Timer();
        MyTask task1 = new MyTask();
        MyTask task2 = new MyTask();
        task2.setInfo("task2-特殊標識");

        // 任務1:固定延遲模式 - 1秒後啟動,每2秒執行
        timer.schedule(task1, 1000, 2000);
        
        // 任務2:固定頻率模式 - 2秒後啟動,每3秒執行
        timer.scheduleAtFixedRate(task2, 2000, 3000);

        // 互動式控制台
        System.out.println("指令: Cancel-1 | Cancel-2 | Cancel-All | 自訂訊息");
        while (true) {
            try {
                byte[] buf = new byte[1024];
                int len = System.in.read(buf);
                String cmd = new String(buf, 0, len, "GBK").trim();
                
                if (cmd.endsWith("\r\n")) cmd = cmd.substring(0, cmd.length() - 2);
                
                switch (cmd) {
                    case "Cancel-1":
                        task1.cancel();
                        System.out.println("任務1已取消");
                        break;
                    case "Cancel-2":
                        task2.cancel();
                        System.out.println("任務2已取消");
                        break;
                    case "Cancel-All":
                        timer.cancel();
                        System.out.println("定時器已完全關閉");
                        return;
                    default:
                        task1.setInfo(cmd); // 動態修改任務1輸出內容
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

    static class MyTask extends TimerTask {
        private String info = "INFO";

        @Override
        public void run() {
            System.out.println(new Date() + " [" + info + "]");
        }
        
        public void setInfo(String info) { this.info = info; }
        public String getInfo() { return info; }
    }
}

關鍵方法對照表

類別方法功能
Timercancel()終止定時器,捨棄所有已排程任務
purge()移除佇列中已取消的任務,釋放記憶體
schedule(task, date)在指定時間單次執行
schedule(task, delay)延遲指定毫秒後單次執行
TimerTaskcancel()取消此任務 (單次任務執行後自動取消)
run()任務執行邏輯 (必須實作)
scheduledExecutionTime()取得最近一次實際排程執行時間

schedule vs scheduleAtFixedRate 差異深度解析

// 固定延遲:執行時間 = 上次結束時間 + period
// 優點:間隔穩定;缺點:長期運行會時間漂移
timer.schedule(task, 0, 1000);

// 固定頻率:執行時間 = 初始時間 + n * period
// 優點:長期時間精準;缺點:若任務耗時 > period 會疊加執行
timer.scheduleAtFixedRate(task, 0, 1000);

實戰最佳實踐建議

  1. 避免在 TimerTask 中耗時操作:會阻塞排程執行緒,影響其他任務。耗時操作應提交至獨立執行緒池
  2. 妥善處理異常:run() 中未捕獲的異常會導致 Timer 執行緒終止,所有任務停止。務必使用 try-catch 包裹
  3. 生產環境建議遷移至 ScheduledExecutorService:支援執行緒池、更好的錯誤處理、關閉控制
  4. 持久化排程需求:需求跨重啟保持、分散式協調時,採用 Quartz 或 Spring @Scheduled

現代替代方案快速對比

方案優點缺點
Timer輕量、API 簡單、JDK 內建單執行緒、異常脆弱、無持久化
ScheduledExecutorService執行緒池、健壯、彈性關閉API 較複雜、無持久化
Spring @Scheduled聲明式、整合 Spring 生命週期、支援 Cron需 Spring 容器、單機模式
Quartz持久化、分散式、Cron 複雜排程配置複雜、較重量級

Timer 作為 JDK 早期提供的定時工具,雖然功能基礎但概念清晰,適合簡單場景與教學用途。掌握其核心機制有助於理解更高階排程框架的設計哲學。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved