1. 程式人生 > >Timer和spring的Quartz兩種定時器的區別。

Timer和spring的Quartz兩種定時器的區別。

這近閒暇無事,研究定時器timer和Quartz。也在網上看了一些例子,大多數要不是講得很籠統就是就得很深奧。仔細想來定時器不就是相當於定時觸發的裝置,這樣想來理解就更容易了。
第一個例子。timer定時器。(這個比較簡單,timer是java.util包下一個類)
為了更好的瞭解,我寫了兩個定時器類,很被整合TimerTask。

public class MyTask extends TimerTask{
            int count = 0; 
 public void run() {
          System.out.println("定時器TimerTask啟動"+count);
         count++;
       }

}
++++++++++++++++++++++++++++++++++++++++++++

public class MyTaskB extends TimerTask{
           int count = 0; 
 public void run() {
         System.out.println("定時器MyTaskB啟動"+count);
        count++;
     }
}
+++++++++++++++++++++++++++++++++++++++++++

在main方法中測試
 Timer timer=new Timer();
 /**
     * 定時器任務制定,執行
     * @param tag: 0.在指定的時間裡,執行指定的任務;
     *             1.在指定的時間裡,按照指定的延遲,重複執行指定任務;
     *             2.從指定的延遲後,執行指定任務;
     *             3.從指定的延遲後,按照指定的延遲,重複執行指定的任務。
     *             
     * @param mydate:指定的執行時間。只有在tag等於0、1才需要指定。            
     * @param delay: 延遲執行時間,毫秒數。只有在tag等於1、3才需要指定。
     * @param period:間隔執行時間,毫秒數。只有在tag等於4才需要指定。
     */ 
     
    //定時器,執行任務測試 
    public static void main(String[] args) {   
     new TestA().timer.schedule(new MyTask(), 1000);
        new TestA().timer.schedule(new MyTaskB(), 4000);
    } 

注:timer還可以在web中應用。直接把MyTask()和MyTaskB()裡面的方法作修改即可,也可以在任務完成後關掉timer定時。
總結:其實timer實現定時任務是很簡單的,但是在想法開發是很少用到timer,而是用spring的Quartz。我也在網上找到了一些資料,現在總結一下。
1. Java定時器沒有持久化機制。
2. Java定時器的日程管理不夠靈活(只能設定開始時間、重複的間隔,設定特定的日期、時間等)//這點感同身受
3. Java定時器沒有使用執行緒池(每個Java定時器使用一個執行緒)//想必在用timer是遇到了吧。
4. Java定時器沒有切實的管理方案,你不得不自己完成儲存、組織、恢復任務的措施

一下例子是我在myeclipse中建立了一個小專案,僅供參考。

第一步建立web專案(省略)

第二步匯入必要包:如下
用到了一下包:
(這九個包我就不多說了,想必大家都知道他的用處。)
第三步:配置相關檔案。web.xml、quartz.properties、quartz_job.xml這三個檔案。這裡我就沒用spring的applicationContext.xml檔案來管理了。其實原理都是一樣,都是在web啟動時監聽並啟動定時器。配置spring的quartz定時器有兩種方法,一種是你用quartz.properties、quartz_job.xml,另外一種是用spring的applicationContext.xml。其實在開發的時候我還是比較喜歡前面一種,因為簡單、方便,而用spring的applicationContext.xml裡面本來就有各種配置,各種注入,是檔案不夠清晰(個人見解。呵呵)
(專案中檔案的位置,直接放在src目錄下)
第四步:web.xml檔案配置(監聽和啟動定時器)

<?xml version="1.0" encoding="UTF-8"?>
<web-app version="2.4"
 xmlns="http://java.sun.com/xml/ns/j2ee"
 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee
 http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd">
 
  <listener>
  <listener-class>
   org.quartz.ee.servlet.QuartzInitializerListener
  </listener-class>
 </listener>
 
 <!--  timer -->
 <context-param>
  <param-name>config-file</param-name>
  <param-value>/quartz.properties</param-value>
 </context-param>
 
 <context-param>
  <param-name>shutdown-on-unload</param-name>
  <param-value>true</param-value>
 </context-param>
 
 
  <welcome-file-list>
    <welcome-file>index.jsp</welcome-file>
  </welcome-file-list>
</web-app>

第五步:配置quartz.properties檔案

org.quartz.scheduler.instanceName = TestScheduler
org.quartz.scheduler.instanceId = one

org.quartz.threadPool.class = org.quartz.simpl.SimpleThreadPool
org.quartz.threadPool.threadCount = 2
org.quartz.threadPool.threadPriority = 4

org.quartz.plugin.jobInitializer.class = org.quartz.plugins.xml.JobInitializationPlugin
org.quartz.plugin.jobInitializer.fileName = quartz_job.xml

註解:主要主用是啟動quartz_job.xml。其餘的都是一些配置效能的屬性,可以在網上檢視。
第六步:配置quartz_job.xml(裡面主要配置定時器的一下屬性)

<?xml version="1.0" encoding="GBK"?>
<quartz>
<!-- 每1分鐘執行一次 -->
 <job>
  <job-detail>
   <name>getDate</name><!-- 表示目標定時器的方法(也就是這個方法要定時的作用)-->
   <group>job</group>
   <job-class>com.timer.util.TimerTask</job-class><!-- 表示上面的getDate()方法路徑(即所在的包)-->
  </job-detail>
  <trigger>
   <cron>
    <name>t1</name>
    <group>job</group>
    <job-name>getDate</job-name>
    <job-group>job</job-group>
    <cron-expression>0 0/1 * * * ?</cron-expression><!-- 設定定時器的觸發時間即間隔時間(引數形式可以在網上查到自己想要的形式)-->
   </cron>
  </trigger>
 </job>

</quartz>

第七步:寫用兩個類來測試定時器是否好用。

public class TimerTask implements Job {

 private static Logger logger = Logger.getLogger(TimerTask.class);

    public void execute(JobExecutionContext arg0) throws JobExecutionException {
        try {
         TimerOperation.getDate();
        } catch (Exception ex) {
            logger.info(ex.getMessage());
        }
    }

}
+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
public class TimerOperation {
 private static Logger logger = Logger.getLogger(TimerOperation.class);
 public static void getDate()
 {
  String strCurrentDateTime = "";
        Date currentDateTime = new Date();
        SimpleDateFormat formatter = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        strCurrentDateTime = formatter.format(currentDateTime);
        logger.info("定時器啟動"+strCurrentDateTime);
 }
}
+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

寫這兩個類就會看出,定時器不能直接呼叫自己寫了定時方法,要先寫一個類實現job的介面,然後在實現介面的execute()方法裡面呼叫自己事先寫好的定時任務。
好了一個定時器就寫好了。執行專案,等待一分鐘控制檯就會出現