DelayQueue延時佇列操作例項
阿新 • • 發佈:2019-02-08
DelayQueue延時佇列,當佇列中的元素到達延遲時間時才會被取出。佇列元素會按照最終執行時間在佇列中進行排序。
最近剛學,本篇先給出一個實際使用的例子。
首先佇列物件當然就是DelayQueue。而佇列元素則需要實現Delayed這個介面,並實現該介面compareTo方法和getDelay方法。
首先定義該元素及其屬性。
class DelayTask implements Delayed {
public String name;
public Long delayTime;
public TimeUnit delayTimeUnit;
public Long executeTime;//ms
DelayTask(String name, long delayTime, TimeUnit delayTimeUnit) {
this.name = name;
this.delayTime = delayTime;
this.delayTimeUnit = delayTimeUnit;
this.executeTime = System.currentTimeMillis() + delayTimeUnit.toMillis(delayTime);
}
}
getDelay方法的作用即是計算當前時間到執行時間之間還有多長時間。
如下,返回unit單位下該延遲時間的值。
@Override
public long getDelay(TimeUnit unit) {
return unit.convert(executeTime - System.currentTimeMillis(), TimeUnit.MILLISECONDS);
}
compareTo方法的作用即是判斷佇列中元素的順序誰前誰後。當前元素比佇列元素後執行時,返回一個正數,比它先執行時返回一個負數,否則返回0.
@Override
public int compareTo(Delayed o) {
if(this.getDelay(TimeUnit.MILLISECONDS) > o.getDelay(TimeUnit.MILLISECONDS)) {
return 1;
}else if(this.getDelay(TimeUnit.MILLISECONDS) < o.getDelay(TimeUnit.MILLISECONDS)) {
return -1;
}
return 0;
}
最後我們用個簡單的方法測試下:
public static void main(String[] args) {
DelayQueue<DelayTask> queue = new DelayQueue<>();
queue.add(new DelayTask("1", 1L, TimeUnit.SECONDS));
queue.add(new DelayTask("2", 2L, TimeUnit.SECONDS));
queue.add(new DelayTask("3", 3L, TimeUnit.SECONDS));
System.out.println("queue put done");
while(!queue.isEmpty()) {
try {
DelayTask task = queue.take();
System.out.println(task.name + ":" + System.currentTimeMillis());
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
執行結果如下:
queue put done
1:1504498317145
2:1504498318145
3:1504498319145
下面是完整的程式碼:
public class DelayQueueTest {
public static void main(String[] args) {
DelayQueue<DelayTask> queue = new DelayQueue<>();
queue.add(new DelayTask("1", 1000L, TimeUnit.MILLISECONDS));
queue.add(new DelayTask("2", 2000L, TimeUnit.MILLISECONDS));
queue.add(new DelayTask("3", 3000L, TimeUnit.MILLISECONDS));
System.out.println("queue put done");
while(!queue.isEmpty()) {
try {
DelayTask task = queue.take();
System.out.println(task.name + ":" + System.currentTimeMillis());
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
class DelayTask implements Delayed {
public String name;
public Long delayTime;
public TimeUnit delayTimeUnit;
public Long executeTime;//ms
DelayTask(String name, long delayTime, TimeUnit delayTimeUnit) {
this.name = name;
this.delayTime = delayTime;
this.delayTimeUnit = delayTimeUnit;
this.executeTime = System.currentTimeMillis() + delayTimeUnit.toMillis(delayTime);
}
@Override
public int compareTo(Delayed o) {
if(this.getDelay(TimeUnit.MILLISECONDS) > o.getDelay(TimeUnit.MILLISECONDS)) {
return 1;
}else if(this.getDelay(TimeUnit.MILLISECONDS) < o.getDelay(TimeUnit.MILLISECONDS)) {
return -1;
}
return 0;
}
@Override
public long getDelay(TimeUnit unit) {
return unit.convert(executeTime - System.currentTimeMillis(), TimeUnit.MILLISECONDS);
}
}