1. 程式人生 > >DelayQueue延時佇列操作例項

DelayQueue延時佇列操作例項

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);
    }

}