Introducción a AQS
El Abstract Queued Synchronizer (AQS) sirve como base para implementar mecenismos de sincronización en Java. Su arquitectura centraliza la gestión de hilos bloqueados y estados de bloqueo, permitiendo construir tanto bloques exclusvios como compartidos.
Bloqueo exclusivo (ejemplo: ReentrantLock)
El proceso de adquisición utiliza CAS para actualizar el estado interno:
- Adquisición exitosa: Estado inicializado a 1 y asociado al hilo actual.
- Adquisición fallida:
- Se crea una cola de espera si no existe
- El hilo se añade a la cola y se bloquea mediante
LockSupport.park()
Para liberar:
- Restablecer el estado a 0
- Eliminar el propietario del blloqueo
- Desbloquear al siguiente hilo en la cola (solo el nodo cabeza)
Bloqueo compartido (ejemplo: Semaphore)
Implementa un control de concurrencia mediante permisos:
public class Semaphore {
private int permitCount;
public void requestPermit() {
while (permitCount <= 0) {
// Añadir a cola y bloquear
}
permitCount--;
}
public void releasePermit() {
permitCount++;
// Desbloquear siguiente hilo
}
}
CountDownLatch
Utiliza AQS en modo compartido para coordinar tareas:
public class CountDownLatch {
private final Synchronizer synchronizer;
public CountDownLatch(int counter) {
synchronizer = new Synchronizer(counter);
}
public void await() throws InterruptedException {
synchronizer.await();
}
public void countDown() {
synchronizer.release();
}
}
CyclicBarrier
Combina bloqueo exclusivo y condiciones para sincronización cíclica:
public class CyclicBarrier {
private final ReentrantLock lock = new ReentrantLock();
private int waitingThreads = 0;
public void await() throws InterruptedException {
lock.lock();
try {
waitingThreads++;
if (waitingThreads == parties) {
// Restablecer contadores
}
} finally {
lock.unlock();
}
}
}
ReentrantReadWriteLock
Implementa lecturas concurrentes y escrituras exclusivas:
- Lecturas: Modo compartido (hasta 16 hilos simultáneos por defecto)
- Escrituras: Modo exclusivo
- Limitaciones: No admite elevación de lectura a escritura
Estado de espera (waitStatus)
Códigos clave para gestión de cola:
CANCELLED (1): Hilo canceladoSIGNAL (-1): Siguiente hilo esperando señalCONDITION (-2): Hilo en cola de condiciónPROPAGATE (-3): Propagación de señal en modo compartido