Trong hướng dẫn này, chúng ta sẽ tìm hiểu về lớp LinkedBLockingQueue và các phương thức của nó với sự trợ giúp của các ví dụ.
Các LinkedBlockingQueue
lớp của Java Collections
framework cung cấp việc thực hiện hàng đợi chặn sử dụng một danh sách liên kết.
Nó thực hiện giao diện Java BlockingQueue .
Tạo LinkedBlockingQueue
Để tạo hàng đợi chặn được liên kết, chúng ta phải nhập java.util.concurrent.LinkedBlockingQueue
gói.
Đây là cách chúng ta có thể tạo một hàng đợi chặn được liên kết trong Java:
1. Nếu không có dung lượng ban đầu
LinkedBlockingQueue<Type> animal = new LinkedBlockingQueue<>();
Ở đây dung lượng ban đầu mặc định sẽ là 2 31 -1.
2. Với công suất ban đầu
LinkedBlockingQueue<Type> animal = new LinkedBlockingQueue<>(int capacity);
Đây,
- Loại – loại hàng đợi chặn được liên kết
- dung lượng – kích thước của hàng đợi chặn được liên kết
Ví dụ,
// Creating String type LinkedBlockingQueue with size 5
LinkedBlockingQueue<String> animals = new LinkedBlockingQueue<>(5);
// Creating Integer type LinkedBlockingQueue with size 5
LinkedBlockingQueue<Integer> age = new LinkedBlockingQueue<>(5);
Lưu ý: Không bắt buộc phải cung cấp kích thước của danh sách liên kết.
Phương thức LinkedBlockingQueue
Các LinkedBlockingQueue
lớp học cung cấp cho việc thực hiện tất cả các phương pháp trong giao diện BlockingQueue .
Các phương pháp này được sử dụng để chèn, truy cập và xóa các phần tử khỏi hàng đợi chặn được liên kết.
Ngoài ra, chúng ta sẽ tìm hiểu về hai phương pháp put()
và take()
hỗ trợ hoạt động chặn trong hàng đợi chặn được liên kết.
Hai phương pháp này phân biệt hàng đợi chặn được liên kết với các hàng đợi điển hình khác.
Chèn phần tử
add()
– Chèn một phần tử được chỉ định vào hàng đợi chặn được liên kết. Nó ném ra một ngoại lệ nếu hàng đợi đã đầy.offer()
– Chèn một phần tử được chỉ định vào hàng đợi chặn được liên kết. Nó trả vềfalse
nếu hàng đợi đã đầy.
Ví dụ,
import java.util.concurrent.LinkedBlockingQueue;
class Main {
public static void main(String[] args) {
LinkedBlockingQueue<String> animals = new LinkedBlockingQueue<>(5);
// Using add()
animals.add("Dog");
animals.add("Cat");
// Using offer()
animals.offer("Horse");
System.out.println("LinkedBlockingQueue: " + animals);
}
}
Đầu ra
LinkedBlockingQueue: [Dog, Cat, Horse]
Phần tử truy cập
peek()
– Trả về một phần tử từ phía trước của hàng đợi chặn được liên kết. Nó trả vềnull
nếu hàng đợi trống.iterator()
– Trả về một đối tượng trình lặp để truy cập tuần tự một phần tử từ hàng đợi chặn được liên kết. Nó ném ra một ngoại lệ nếu hàng đợi trống. Chúng ta phải nhậpjava.util.Iterator
gói để sử dụng nó.
Ví dụ,
import java.util.concurrent.LinkedBlockingQueue;
import java.util.Iterator;
class Main {
public static void main(String[] args) {
LinkedBlockingQueue<String> animals = new LinkedBlockingQueue<>(5);
// Add elements
animals.add("Dog");
animals.add("Cat");
animals.add("Horse");
System.out.println("LinkedBlockingQueue: " + animals);
// Using peek()
String element = animals.peek();
System.out.println("Accessed Element: " + element);
// Using iterator()
Iterator<String> iterate = animals.iterator();
System.out.print("LinkedBlockingQueue Elements: ");
while(iterate.hasNext()) {
System.out.print(iterate.next());
System.out.print(", ");
}
}
}
Đầu ra
LinkedBlockingQueue: [Dog, Cat, Horse] Phần tử được truy cập: Con chó LinkedBlockingQueue Elements: Dog, Cat, Horse,
Xóa các phần tử
remove()
– Trả về và xóa một phần tử được chỉ định khỏi hàng đợi chặn được liên kết. Nó ném ra một ngoại lệ nếu hàng đợi trống.poll()
– Trả về và xóa một phần tử được chỉ định khỏi hàng đợi chặn được liên kết. Nó trả vềnull
nếu hàng đợi trống.clear()
– Loại bỏ tất cả các phần tử khỏi hàng đợi chặn được liên kết.
Ví dụ,
import java.util.concurrent.LinkedBlockingQueue;
class Main {
public static void main(String[] args) {
LinkedBlockingQueue<String> animals = new LinkedBlockingQueue<>(5);
animals.add("Dog");
animals.add("Cat");
animals.add("Horse");
System.out.println("LinkedBlockingQueue " + animals);
// Using remove()
String element1 = animals.remove();
System.out.println("Removed Element:");
System.out.println("Using remove(): " + element1);
// Using poll()
String element2 = animals.poll();
System.out.println("Using poll(): " + element2);
// Using clear()
animals.clear();
System.out.println("Updated LinkedBlockingQueue " + animals);
}
}
Đầu ra
LinkedBlockingQueue: [Dog, Cat, Horse] Các phần tử đã loại bỏ: Sử dụng remove (): Dog Sử dụng thăm dò ý kiến (): Cat Đã cập nhật LinkedBlockingQueue: []
Phương thức put () và take ()
Trong quy trình đa luồng, chúng ta có thể sử dụng put()
và take()
chặn hoạt động của một luồng để đồng bộ hóa nó với một luồng khác. Các phương thức này sẽ đợi cho đến khi chúng có thể được thực thi thành công.
phương thức put ()
Để chèn phần tử được chỉ định vào cuối hàng đợi chặn được liên kết, chúng tôi sử dụng put()
phương pháp.
Nếu hàng đợi chặn được liên kết đã đầy, nó sẽ đợi cho đến khi có khoảng trống trong hàng đợi chặn được liên kết để chèn phần tử.
Ví dụ,
import java.util.concurrent.LinkedBlockingQueue;
class Main {
public static void main(String[] args) {
LinkedBlockingQueue<String> animals = new LinkedBlockingQueue<>(5);
try {
// Add elements to animals
animals.put("Dog");
animals.put("Cat");
System.out.println("LinkedBlockingQueue: " + animals);
}
catch(Exception e) {
System.out.println(e);
}
}
}
Đầu ra
LinkedBlockingQueue: [Dog, Cat]
Ở đây, put()
phương thức có thể ném ra InterruptedException
nếu nó bị gián đoạn trong khi chờ đợi. Do đó, chúng ta phải đặt nó bên trong một khối try..catch .
phương thức take ()
Để trả về và xóa một phần tử khỏi hàng đợi chặn được liên kết, chúng ta có thể sử dụng take()
phương pháp này.
Nếu hàng đợi chặn được liên kết trống, nó sẽ đợi cho đến khi có các phần tử trong hàng đợi chặn được liên kết bị xóa.
Ví dụ,
import java.util.concurrent.LinkedBlockingQueue;
class Main {
public static void main(String[] args) {
LinkedBlockingQueue<String> animals = new LinkedBlockingQueue<>(5);
try {
//Add elements to animals
animals.put("Dog");
animals.put("Cat");
System.out.println("LinkedBlockingQueue: " + animals);
// Remove an element
String element = animals.take();
System.out.println("Removed Element: " + element);
System.out.println("New LinkedBlockingQueue: " + animals);
}
catch(Exception e) {
System.out.println(e);
}
}
}
Đầu ra
LinkedBlockingQueue: [Dog, Cat] Phần tử đã xóa: Con chó LinkedBlockingQueue mới: [Cat]
Ở đây, take()
phương thức sẽ ném ra một InterrupedException
nếu nó bị gián đoạn trong khi chờ đợi. Do đó, chúng ta phải đặt nó bên trong một try...catch
khối.
Các phương pháp khác
Phương pháp | Mô tả |
---|---|
contains(element) | Tìm kiếm hàng đợi chặn được liên kết cho phần tử được chỉ định. Nếu phần tử được tìm thấy, nó sẽ trả về true , nếu không nó sẽ trả về false . |
size() | Trả về độ dài của hàng đợi chặn được liên kết. |
toArray() | Chuyển đổi hàng đợi chặn được liên kết thành một mảng và trả về mảng. |
toString() | Chuyển đổi hàng đợi chặn được liên kết thành chuỗi |
Tại sao sử dụng LinkedBlockingQueue?
Các LinkedBlockingQueue
sử dụng danh sách liên kết như lưu trữ nội bộ của mình.
Nó được coi là một bộ sưu tập an toàn theo chủ đề . Do đó, nó thường được sử dụng trong các ứng dụng đa luồng.
Giả sử, một luồng đang chèn các phần tử vào hàng đợi và một luồng khác đang xóa các phần tử khỏi hàng đợi.
Bây giờ, nếu luồng đầu tiên chậm hơn luồng thứ hai, thì hàng đợi chặn được liên kết có thể khiến luồng thứ hai đợi cho đến khi luồng đầu tiên hoàn thành các hoạt động của nó.