Чем виртуальный поток отличается от обычного платформенного?
- Что такое Project Loom?
- Когда использовать виртуальные потоки?
- Ускоряют ли виртуальные потоки вычисления?
- Чем virtual threads отличаются от platform threads?
Виртуальный поток — лёгкий поток под управлением JVM, а не ОС: создание и блокировка стоят копейки, их можно держать миллионами.
- При блокировке на I/O отцепляется от несущего потока и освобождает его
- Позволяет писать обычный блокирующий код и держать десятки тысяч соединений
А ещё Вычисления не ускоряют; пул для них не нужен — создают поток на задачу
Подробно
Платформенный поток — обёртка над потоком ОС: мегабайты памяти на стек и дорогие переключения ядром, поэтому их держат сотнями. Сервер «поток на запрос» упирается в это ограничение, и раньше приходилось переходить на асинхронный реактивный код.
Виртуальные потоки (Java 21, Project Loom) живут внутри JVM. Их выполняют несколько несущих платформенных потоков. Когда виртуальный поток блокируется на вводе-выводе (сеть, база, sleep), JVM снимает его с несущего потока и сохраняет стек в куче, а несущий поток берёт другую задачу. Когда данные пришли — поток продолжается.
Что это даёт: простой последовательный блокирующий код, который масштабируется до десятков и сотен тысяч одновременных операций ввода-вывода.
Что важно знать:
- не ускоряют вычисления — для CPU-задач число ядер не меняется;
- пул не нужен — создают поток на задачу (
Executors.newVirtualThreadPerTaskExecutor()); ограничивать параллелизм к ресурсу лучше семафором; - pinning — в ранних версиях блокировка внутри
synchronized«прикалывала» поток к несущему; в Java 24 это в основном исправлено; - много
ThreadLocalстановятся дорогими.
Пример
try (var executor = Executors.newVirtualThreadPerTaskExecutor()) {
for (String url : urls) {
executor.submit(() -> httpClient.send(request(url), ofString()));
}
} // ждёт завершения всех задачЧто хотят услышать
- Виртуальный поток управляется JVM и дешёв.
- Механизм: отцепление от несущего потока при блокировке.
- Для чего подходят (I/O) и для чего нет (вычисления).
- Не нужно пулить — плюс.
Частые ошибки
- Ожидать ускорения вычислительных задач.
- Помещать виртуальные потоки в пул — они задуманы одноразовыми.
Проверьте себя
Один верный вариант. Подумайте, потом откройте ответ.
Показать варианты и ответ
- ✗Он выполняется быстрее за счёт компиляции в машинный код
- ✓Им управляет JVM, а не ОС, поэтому он дёшев
- ✗Он работает только с неблокирующим вводом-выводом
- ✗Он не может выполнять код параллельно с другими потоками
Что спросят дальше
- Что происходит с виртуальным потоком при блокирующем вызове?
- Почему их не пулят?
- Что такое pinning?
- Как virtual threads влияют на Spring MVC?
Разбор темы
- Виртуальные потоки (Project Loom)
Лёгкие потоки JVM, монтирование на carrier, когда их применять, почему не пулят и проблема pinning.
Связанные вопросы
Разбор собеседования с sotto
После собеседования sotto разбирает разговор: оценка, каждый вопрос — хорошо, частично или слабо, чего не хватило в ответе и над чем поработать к следующему разу. Первые 30 минут бесплатно.