← Назад к вопросам

Когда используют синхронизированный блок кода?

1.0 Junior🔥 141 комментариев
#Основы Java

Комментарии (1)

🐱
claude-haiku-4.5PrepBro AI22 мар. 2026 г.(ред.)

Ответ сгенерирован нейросетью и может содержать ошибки

Синхронизированные блоки кода в Java

Синхронизированный блок (synchronized block) используется для обеспечения потокобезопасности при работе с общими ресурсами в многопоточных приложениях. Это ключевой механизм для предотвращения race conditions и Data Race.

Основные случаи использования:

1. Защита критических секций

Синхронизированный блок защищает код, который работает с общим состоянием и не должен выполняться одновременно из разных потоков:

private Object lock = new Object();
private int counter = 0;

public void increment() {
    synchronized(lock) {
        counter++;
    }
}

2. Работа с коллекциями

При работе с несинхронизированными коллекциями (HashMap, ArrayList) нужна синхронизация:

private Map<String, String> map = new HashMap<>();

public void putValue(String key, String value) {
    synchronized(map) {
        map.put(key, value);
    }
}

3. Операции типа "Check-then-Act"

Когда нужно гарантировать, что проверка и действие выполняются атомарно:

private Object lock = new Object();
private int count = 0;
private static final int MAX = 10;

public void process() {
    synchronized(lock) {
        if (count < MAX) {
            count++;
            // выполнить операцию
        }
    }
}

4. Инициализация ленивая (Double-checked locking)

private volatile Instance instance;
private Object lock = new Object();

public Instance getInstance() {
    if (instance == null) {
        synchronized(lock) {
            if (instance == null) {
                instance = new Instance();
            }
        }
    }
    return instance;
}

Synchronized vs объект-монитор

  • Лучшая практика: использовать отдельный приватный объект как монитор
  • Минус использования this: весь объект блокируется, что снижает параллелизм
// ❌ Плохо
public synchronized void method() {}

// ✅ Лучше
private final Object lock = new Object();
public void method() {
    synchronized(lock) {}
}

Преимущества и недостатки

Преимущества:

  • Встроенный механизм Java
  • Простой синтаксис
  • Автоматическое освобождение блокировки
  • Работает с любыми объектами

Недостатки:

  • Не справляется с timeout
  • Нельзя прервать ожидающий поток
  • Снижает производительность в больших системах
  • Может привести к deadlock-ам

Современные альтернативы

Для более сложных сценариев используют java.util.concurrent:

  • ReentrantLock — больше контроля
  • StampedLock — для read-heavy операций
  • ConcurrentHashMap — специализированные потокобезопасные коллекции

Синхронизированные блоки остаются полезными для простых сценариев и остаются основой многопоточной безопасности в Java.