Ați lucrat cu semafoare în practica dvs.?
sobes.tech AI
Răspuns de la AI
Da, a fost nevoie să folosesc semafoare, în special în contextul lucrului cu multithreading în aplicațiile Android.
Semafoarele în Java (java.util.concurrent.Semaphore) sunt folosite pentru a limita numărul de fire de execuție care pot accesa simultan o anumită resursă. Acest lucru este util în scenarii în care resursa are o "capacitate" limitată, de exemplu, un pool de conexiuni sau un număr limitat de sloturi disponibile.
Metodele principale cu care am lucrat sunt:
acquire(): Blochează firul de execuție curent până când o permisiune devine disponibilă.acquire(int permits): Blochează firul de execuție curent până când numărul specificat de permisiuni este disponibil.release(): Returnează o permisiune semaforului, mărind numărul de permisiuni disponibile.release(int permits): Returnează numărul specificat de permisiuni.tryAcquire(): Încearcă să obțină o permisiune fără a bloca firul de execuție.availablePermits(): Returnează numărul curent de permisiuni disponibile.
Exemplu de utilizare:
import java.util.concurrent.Semaphore;
public class ResourcePool {
private static final int MAX_AVAILABLE = 5;
private final Semaphore permits = new Semaphore(MAX_AVAILABLE, true); // Semafor echitabil
public void useResource() throws InterruptedException {
permits.acquire(); // Solicită permisiune
try {
// Logica de utilizare a resursei (de exemplu, lucrul cu un pool de conexiuni)
System.out.println(Thread.currentThread().getName() + " folosind resursa.");
Thread.sleep(1000); // Simulare de lucru cu resursa
} finally {
permits.release(); // Eliberează permisiunea
System.out.println(Thread.currentThread().getName() + " a terminat de folosit resursa.");
}
}
public static void main(String[] args) {
ResourcePool pool = new ResourcePool();
// Creăm mai multe fire de execuție care vor încerca să folosească resursa
for (int i = 0; i < 10; i++) {
new Thread(() -> {
try {
pool.useResource();
} catch (InterruptedException e) {
e.printStackTrace();
}
}).start();
}
}
}
În acest exemplu, semaforul permits este inițializat cu 5 permisiuni, ceea ce înseamnă că doar 5 fire de execuție pot fi în blocul try care utilizează resursa în același timp. Metoda acquire() blochează firele dacă toate permisiunile sunt ocupate, până când alte fire apelează release().
Semafoarele sunt utile pentru gestionarea accesului la pool-uri de resurse limitate, dar trebuie avut grijă la problemele potențiale precum deadlock-urile, dacă gestionarea obținerii și eliberării permisiunilor nu este corectă. Utilizarea try cu un bloc finally pentru apelarea release() este o practică bună pentru a asigura eliberarea resurselor chiar și în caz de excepții.