Что выступает монитором для нестатического synchronized метода в Java?

Ответ

Монитором (встроенной блокировкой) для нестатического synchronized метода является экземпляр объекта (this), у которого этот метод вызывается.

Ключевые моменты:

  • Каждый объект в Java имеет связанный с ним монитор (intrinsic lock).
  • Когда поток входит в synchronized метод, он захватывает монитор этого конкретного объекта.
  • Другие потоки будут заблокированы при попытке войти в любой synchronized метод (или synchronized(this) блок) этого же экземпляра, пока первый поток не освободит монитор.

Пример:

public class BankAccount {
    private int balance;

    // Монитором для этого метода служит экземпляр BankAccount
    public synchronized void deposit(int amount) {
        balance += amount;
    }

    public synchronized void withdraw(int amount) {
        if (balance >= amount) {
            balance -= amount;
        }
    }
}

BankAccount account1 = new BankAccount();
BankAccount account2 = new BankAccount();

// Поток 1: Захватывает монитор account1
account1.deposit(100);

// Поток 2: Может работать с account2 параллельно (это другой монитор).
account2.withdraw(50);

// Поток 3: Будет ждать, если попытается вызвать account1.withdraw() пока Поток 1 не выйдет из deposit().

Эквивалентная запись с явной блокировкой:

public void deposit(int amount) {
    synchronized(this) { // Явное указание на монитор объекта
        balance += amount;
    }
}

Ответ 18+ 🔞

Слушай, а вот этот твой вопрос про synchronized методы — это ж классика, блядь! Прям как в том анекдоте про Герасима и Муму, только про потоки. Ну ладно, ща объясню, чтобы у тебя в голове не было как у того немого — «ууууу, блядь».

Так вот, смотри. Когда ты пишешь этот самый synchronized для обычного, нестатического метода, то монитором — этой самой дверью, которую захлопывают, чтобы никто другой не влез — служит сам объект, this, конкретный экземпляр, ёпта!

Представь себе, у тебя есть банковский счёт, BankAccount. Это как Герасим, здоровый мужик, но со своим внутренним замком.

public class BankAccount {
    private int balance;

    // Монитором для этого метода служит экземпляр BankAccount
    public synchronized void deposit(int amount) {
        balance += amount; // Положил бабки
    }
}

Вот что происходит, когда поток заходит в deposit:

  1. Поток подходит к объекту account1 и говорит: «Так, Герасим, дай-ка сюда твой монитор, твой внутренний замок».
  2. Захватывает его, блядь! Всё, теперь он хозяин положения.
  3. Пока он там ковыряется с балансом, любой другой поток, который захочет вызвать ЛЮБОЙ synchronized метод этого же самого account1 (или залезть в synchronized(this) блок), будет стоять и ждать, как дурак! Ему скажут: «Муму!», то есть «Пошёл нахуй, монитор занят!».
  4. Как только первый поток выйдет из метода — он отпустит замок. И тогда уже следующий сможет зайти.

А теперь самое интересное, блядь, где многие ебутся! Если у тебя два разных объекта — это как два разных Герасима, у каждого свой замок!

BankAccount account1 = new BankAccount(); // Герасим №1
BankAccount account2 = new BankAccount(); // Герасим №2, совсем другой мужик

// Поток 1: Захватывает монитор account1. Сидит у Герасима №1 в сарае.
account1.deposit(100);

// Поток 2: Ему похуй на Герасима №1! Он спокойно идёт к Герасиму №2 и работает с account2.
account2.withdraw(50); // Никаких проблем, параллельно!

// Поток 3: А вот если он полезет к account1, пока Поток 1 не закончил — вот тут его и накроет, блядь! Будет ждать, как та Муму у озера.

И эта вся магия с synchronized методом — она просто короткая запись, сахар такой, ёпта. Можно сделать то же самое явно, чтоб прям видно было:

public void deposit(int amount) {
    synchronized(this) { // Смотри-ка, блядь! Прямо указываю: «Замок — это этот самый объект!»
        balance += amount;
    }
}

Вот и вся история, блядь. Не надо тут выебываться с какими-то глобальными замками. Каждый объект — сам себе Герасим со своим монитором. Захотел потокам безопасно работать с одним объектом — синхронизируйся по нему. Захотел, чтобы они друг другу не мешали с разными объектами — да похуй, работают параллельно. Главное — не утопить свою Муму в конце, а то совесть замучает, как у Тургенева, блядь.