Hướng dẫn dùng semaphores trong PHP

Bài viết được sự cho phép của tác giả Giang Phan

Semaphore là một cơ chế giúp quản lý các nguồn chia sẻ và đảm bảo access không bị tắc nghẽn.

Có hai loại semaphore: binary semaphore và counting semaphore.

  • Binary semaphore [Mutex]: được dùng làm lock vì nó chỉ có 2 giá trị là 0 và 1. Hai giá trị này đại diện cho trạng thái lock hay unlock.
  • Counting semaphore: thực hiện đếm resource để cho biết mức độ sẵn sàng của resource.

Xem thêm tuyển dụng Java lương hấp dẫn trên TopDev

Cơ chế hoạt động

Một Semaphore lưu trữ một danh sách các permit [hay ticket], mỗi khi gọi acquire[] sẽ lấy 1 ticket từ Semaphore, mỗi khi gọi release[] sẽ trả ticket về Semaphore. Nếu ticket không có sẵn, acquire[] sẽ bị lock cho đến khi có ticket. Để kiểm tra số lượng ticket còn lại, sử dụng phương thức availablePermits[].

Ví dụ chúng ta gọi các phương thức tuần tự như sau:

// Tạo một Semaphore có 5 ticket
Semaphore semaphore = new Semaphore[5];

// Yêu cầu lấy 1 ticket để sử dụng
semaphore.acquire[]; // 5-1

// Đếm về số lượng ticket có sẵn
int numberOfAvailableTickets = semaphore.availablePermits[]; // 4

// Trả 1 ticket về Semaphore
semaphore.release[]; // 4+1

// Đếm về số lượng ticket có sẵn
semaphore.availablePermits[]; // 5

Ví dụ sử dụng Semaphore

Giả sử một ngân hàng có 4 cây ATM, mỗi cây chỉ có thể phục vụ được một khách hàng tại một thời điểm. Chương trình bên dưới cho thấy Semaphore có thể đảm bảo chỉ tối đa 4 người có thể truy cập tại một thời điểm.

WorkerThread.java

package com.gpcoder.semaphore;

import java.util.concurrent.Semaphore;

public class WorkerThread extends Thread {

private final Semaphore semaphore;
private String name;

public WorkerThread[Semaphore semaphore, String name] {
this.semaphore = semaphore;
this.name = name;
}

public void run[] {
try {
System.out.println[name + ": acquiring lock..."];
System.out.println[name + ": available Semaphore permits now: " + semaphore.availablePermits[]];
semaphore.acquire[];
System.out.println[name + ": got the permit!"];

try {
System.out.println[name + ": is performing operation, available Semaphore permits : "
+ semaphore.availablePermits[]];
Thread.sleep[100]; // simulate time to work
} finally {
// calling release[] after a successful acquire[]
System.out.println[name + ": releasing lock..."];
semaphore.release[];
System.out.println[name + ": available Semaphore permits now: " + semaphore.availablePermits[]];
}
} catch [InterruptedException e] {
e.printStackTrace[];
}
}
}

SemaphoreExample.java

package com.gpcoder.semaphore;

import java.util.concurrent.Semaphore;

public class SemaphoreExample {

private static Semaphore semaphore = new Semaphore[4];

public static void main[String[] args] {
System.out.println["Total available Semaphore permits: " + semaphore.availablePermits[]];
for [int i = 1; i 

Chủ Đề