首頁 > 軟體

Java執行緒池佇列PriorityBlockingQueue和SynchronousQueue詳解

2022-12-13 14:00:21

正文

public enum QueueTypeEnum {
    ARRAY_BLOCKING_QUEUE(1, "ArrayBlockingQueue"),
    LINKED_BLOCKING_QUEUE(2, "LinkedBlockingQueue"),
    DELAY_QUEUE(3, "DelayQueue"),
    PRIORITY_BLOCKING_QUEUE(4, "PriorityBlockingQueue"),
    SYNCHRONOUS_QUEUE(5, "SynchronousQueue"),
    LINKED_TRANSFER_QUEUE(6, "LinkedTransferQueue"),
    LINKED_BLOCKING_DEQUE(7, "LinkedBlockingDeque"),
    VARIABLE_LINKED_BLOCKING_QUEUE(8, "VariableLinkedBlockingQueue"),
    MEMORY_SAFE_LINKED_BLOCKING_QUEUE(9, "MemorySafeLinkedBlockingQueue");
}

PriorityBlockingQueue阻塞優先佇列

一個支援優先順序排序的無界阻塞佇列;對元素沒有要求,可以實現Comparable介面也可以提供 Comparator來對佇列中的元素進行比較。通過建構函式傳入的物件來判斷,傳入的物件必須實現comparable介面,並重寫compareTo方法。可以按照自然排序或自定義排序的順序在佇列中對元素進行排序

例如新建物件Person:

public class Person implements Comparable<Person>{
private int id;
@Override
public int compareTo(Person person) {
        return this.id > person.getId() ? 1 : ( this.id < person.getId() ? -1 :0);
}
}

每次新增一個元素,PriorityBlockingQueue中的person都會執行compareTo方法進行排序,但是隻是把第一個元素排在首位,其他元素按照佇列的一系列複雜演演算法排序。這就保障了每次獲取到的元素都是經過排序的第一個元素

SynchronousQueue

SynchronousQueue是一個不儲存元素的阻塞佇列,是BlockingQueue的一種,SynchronousQueue執行緒安全的。SynchronousQueue和其他的BlockingQueue不同的是SynchronousQueue的capacity是0。即SynchronousQueue不儲存任何元素。消費者執行緒呼叫 take() 方法的時候就會發生阻塞,直到有一個生產者執行緒生產了一個元素,消費者執行緒就可以拿到這個元素並返回;生產者執行緒呼叫 put() 方法的時候也會發生阻塞,直到有一個消費者執行緒消費了一個元素,生產者才會返回。

SynchronousQueue內部並沒有資料快取空間,你不能呼叫peek()方法來看佇列中是否有資料元素,因為資料元素只有當你試著取走的時候才可能存在,不取走而只想偷 窺一下是不行的,當然遍歷這個佇列的操作也是不允許的。

佇列頭元素是第一個排隊要插入資料的執行緒,而不是要交換的資料。資料是在配對的生產者和消費者執行緒之間直接傳遞的,並不會將資料緩衝到佇列中。可以這樣來理解:生產者和消費者互相等待對方,握手,然後一起離開。

SynchronousQueue的一個使用場景是線上程池裡。Executors.newCachedThreadPool()就使用了SynchronousQueue,這個執行緒池根據需要(新任務到來時)建立新的執行緒,如果有空閒執行緒則會重複使用,執行緒空閒了60秒後會被回收。 

以上就是Java執行緒池佇列PriorityBlockingQueue和SynchronousQueue詳解的詳細內容,更多關於Java執行緒池佇列的資料請關注it145.com其它相關文章!


IT145.com E-mail:sddin#qq.com