Senior
Ikki foydalanuvchi bir vaqtning o'zida teatrda bir joy uchun chipta sotib olayotganda, faqat bitta foydalanuvchiga joy berilishini qanday ta'minlash mumkin?
sobes.tech AI
AIdan javob
Чтобы гарантировать, что два пользователя не смогут одновременно купить одно и то же место, нужно обеспечить атомарность операции бронирования. В Java это можно сделать несколькими способами:
-
Синхронизация на уровне приложения:
- Использовать synchronized-блок или ReentrantLock, чтобы только один поток мог проверить и забронировать место в один момент времени.
-
Использование транзакций и блокировок на уровне базы данных:
- В базе данных, где хранится информация о местах, использовать транзакцию с блокировкой записи (например, SELECT ... FOR UPDATE).
- При попытке забронировать место, транзакция проверяет, свободно ли оно, и если да — помечает как занятое.
- Если два запроса идут одновременно, один из них заблокирует запись, второй будет ждать или получит ошибку.
-
Оптимистичная блокировка:
- Использовать версионность записи (например, поле version).
- При обновлении проверять, что версия не изменилась с момента чтения.
- Если изменилась — повторить попытку.
Пример с synchronized:
public class Theater {
private final Set<Integer> bookedSeats = new HashSet<>();
public synchronized boolean bookSeat(int seatNumber) {
if (bookedSeats.contains(seatNumber)) {
return false; // уже занято
} else {
bookedSeats.add(seatNumber);
return true; // успешно забронировано
}
}
}
В реальных системах предпочтительнее использовать транзакции базы данных, так как они обеспечивают согласованность данных при масштабировании и работе нескольких приложений.