ScheduledExecutorService



先來個傳統的Timer的例子:

  1. package com.jerry.concurrency;  
  2.   
  3. import java.text.ParseException;  
  4. import java.text.SimpleDateFormat;  
  5. import java.util.Date;  
  6. import java.util.Timer;  
  7. import java.util.TimerTask;  
  8.   
  9. public class TraditionalTask {  
  10.       
  11.   
  12.     public static void main(String[] args) throws ParseException {  
  13.         Timer myTimer = new Timer();  
  14.         myTimer.schedule(new Worker(), 1000);//1秒後執行  
  15. //      2012-02-28 09:58:00執行  
  16.         myTimer.schedule(new Worker(), new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").parse("2012-02-28 09:58:00"));  
  17.         myTimer.schedule(new Worker(), 5000,1000);//5秒後執行 每一秒執行一次  
  18. //      2012-02-28 09:58:00執行一次 以後每秒執行一次,如果設定的時間點在當前時間之前,任務會被馬上執行,然後開始按照設定的週期定時執行任務  
  19.         myTimer.schedule(new Worker(), new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").parse("2012-02-28 09:58:00"),1000);  
  20.         myTimer.scheduleAtFixedRate(new Worker(), 5000,1000);//5秒後執行 每一秒執行一次 如果該任務因爲某些原因(例如垃圾收集)而延遲執行,那麼接下來的任務會儘可能的快速執行,以趕上特定的時間點  
  21.         myTimer.scheduleAtFixedRate(new Worker(), new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").parse("2012-02-28 09:58:00"),1000);//和上個類似  
  22.     }  
  23. }  
  24.   
  25.   
  26. class Worker extends TimerTask {  
  27.   
  28.     @Override  
  29.     public void run() {  
  30.           
  31.         System.out.println("我被執行了!"+"時間是:"+new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));  
  32.     }  
  33.       
  34. }  
package com.jerry.concurrency;

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Timer;
import java.util.TimerTask;

public class TraditionalTask {
	

	public static void main(String[] args) throws ParseException {
		Timer myTimer = new Timer();
		myTimer.schedule(new Worker(), 1000);//1秒後執行
//		2012-02-28 09:58:00執行
		myTimer.schedule(new Worker(), new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").parse("2012-02-28 09:58:00"));
		myTimer.schedule(new Worker(), 5000,1000);//5秒後執行 每一秒執行一次
//		2012-02-28 09:58:00執行一次 以後每秒執行一次,如果設定的時間點在當前時間之前,任務會被馬上執行,然後開始按照設定的週期定時執行任務
		myTimer.schedule(new Worker(), new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").parse("2012-02-28 09:58:00"),1000);
		myTimer.scheduleAtFixedRate(new Worker(), 5000,1000);//5秒後執行 每一秒執行一次 如果該任務因爲某些原因(例如垃圾收集)而延遲執行,那麼接下來的任務會儘可能的快速執行,以趕上特定的時間點
		myTimer.scheduleAtFixedRate(new Worker(), new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").parse("2012-02-28 09:58:00"),1000);//和上個類似
	}
}


class Worker extends TimerTask {

	@Override
	public void run() {
		
		System.out.println("我被執行了!"+"時間是:"+new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
	}
	
}

傳統的timer的缺點:Timer對任務的調度是基於絕對時間的;所有的TimerTask只有一個線程TimerThread來執行,因此同一時刻只有一個TimerTask在執行;任何一個TimerTask的執行異常都會導致Timer終止所有任務;由於基於絕對時間並且是單線程執行,因此在多個任務調度時,長時間執行的任務被執行後有可能導致短時間任務快速在短時間內被執行多次或者乾脆丟棄多個任務。

ScheduledExecutorService克服了上述缺點,例子如下:

  1. <span style="font-family: Verdana, Geneva, Arial, Helvetica, sans-serif; font-size: 13px;">package com.jerry.concurrency;  
  2.   
  3.   
  4. import java.util.concurrent.Executors;  
  5. import java.util.concurrent.ScheduledExecutorService;  
  6. import java.util.concurrent.TimeUnit;  
  7.   
  8.   
  9.   
  10.   
  11. public class TestScheduledExecutorService{  
  12.     public static void main(String[] args) throws Exception{  
  13.         ScheduledExecutorService execService =   Executors.newScheduledThreadPool(3);  
  14.         // 5秒後開始執行 每個2秒執行一次,如果有的任務執行要花費比其週期更長的時間,則將推遲後續執行,但不會同時執行  
  15. //        每次相隔相同的時間執行任務,如果任務的執行時間比周期還長,那麼下一個任務將立即執行  
  16.         execService.scheduleAtFixedRate(new Runnable() {  
  17.             public void run() {  
  18.                 System.out.println("任務:"+Thread.currentThread().getName()+" 執行了,時間爲: "+System.currentTimeMillis());  
  19.                 try {  
  20.                     Thread.sleep(1000L);  
  21.                 } catch (Exception e) {  
  22.                     e.printStackTrace();  
  23.                 }  
  24.             }  
  25.         }, 52, TimeUnit.SECONDS);  
  26.         //5秒後開始執行 每個2秒執行一次,保證固定的延遲爲2秒 下一個任務的開始時間與上一個任務的結束時間間隔相同  
  27.         execService.scheduleWithFixedDelay(new Runnable() {  
  28.             public void run() {  
  29.                 System.out.println("任務:"+Thread.currentThread().getName()+"執行了,時間爲:"+System.currentTimeMillis());  
  30.                 try {  
  31.                     Thread.sleep(1000L);  
  32.                 } catch (Exception e) {  
  33.                     e.printStackTrace();  
  34.                 }  
  35.             }  
  36.         }, 52, TimeUnit.SECONDS);  
  37.         Thread.sleep(10000L);  
  38.         execService.shutdown();  
  39.     }  
  40. }  
  41. </span>  
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章