Python GIL убивает многопоточность или можно обойтись

Рейтинг: 64.6% · 7 голосов
Python, Rust, Go, C++, C#, Java, Kotlin: синтаксис, паттерны проектирования, производительность, многопоточность и сравнение языков.
Ответить
Аватара пользователя
oleg
Сообщения: 9
Зарегистрирован: Пн май 11, 2026 12:03 am

Python GIL убивает многопоточность или можно обойтись

Сообщение oleg »

Пишу сервис на Python 3.11, который параллельно обрабатывает входящие JSON-запросы и делает CPU-тяжёлые вычисления — нормализация данных, агрегация по большим массивам. Запустил ThreadPoolExecutor с 8 воркерами, мониторю через htop — все ядра простаивают, реально работает одно. Читал про GIL, но так и не понял: это вообще решаемо без переписывания на другой язык?
👍 ❤️ 🔥1 😄1 🤔
✔ Лучший ответ выбран автором и совпадает с автоматическим подбором — yegor_lab
GIL блокирует именно CPU-bound задачи в потоках — это фундаментальное ограничение CPython. Для твоего кейса нужен ProcessPoolExecutor вместо ThreadPoolExecutor: каждый процесс получает свой интерпретатор и свой GIL. Примерно так: from concurrent.futures import ProcessPoolExecutor; with ProcessPoolExecutor(max_workers=8) as ex: results = list(ex.map(process_item, data)). Накладные расходы на сериа…
Перейти к ответу →
Аватара пользователя
yegor_lab
Сообщения: 1
Зарегистрирован: Пт май 22, 2026 6:56 am

Re: Python GIL убивает многопоточность или можно обойтись

Сообщение yegor_lab »

✔ Лучший ответ — выбран автором и совпадает с авто-подбором
GIL блокирует именно CPU-bound задачи в потоках — это фундаментальное ограничение CPython. Для твоего кейса нужен ProcessPoolExecutor вместо ThreadPoolExecutor: каждый процесс получает свой интерпретатор и свой GIL. Примерно так: from concurrent.futures import ProcessPoolExecutor; with ProcessPoolExecutor(max_workers=8) as ex: results = list(ex.map(process_item, data)). Накладные расходы на сериализацию через pickle есть, но для тяжёлых вычислений это окупается.
👍 ❤️ 🔥 😄 🤔
Аватара пользователя
igor9147
Сообщения: 1
Зарегистрирован: Пн май 11, 2026 9:58 am

Re: Python GIL убивает многопоточность или можно обойтись

Сообщение igor9147 »

Ещё вариант — NumPy и SciPy. Большинство их операций реализованы на C и освобождают GIL на время выполнения. Если твоя агрегация ложится на векторные операции numpy, можешь получить реальный параллелизм даже в потоках, без смены архитектуры. Проверь, можно ли переписать узкое место под np.sum / np.mean / np.vectorize.
👍 ❤️ 🔥1 😄1 🤔1
Аватара пользователя
roman_sigma
Сообщения: 13
Зарегистрирован: Пн май 11, 2026 2:24 am

Re: Python GIL убивает многопоточность или можно обойтись

Сообщение roman_sigma »

Python 3.13 наконец-то добавил экспериментальный режим без GIL (--disable-gil / free-threaded build). Но это пока не продакшн, у меня на синтетических тестах были странные краши при интенсивном shared state. Следи за PEP 703, там всё расписано. Для серьёзного проекта сейчас я бы не рисковал.
👍 ❤️ 🔥 😄 🤔
Аватара пользователя
appdev1427
Сообщения: 6
Зарегистрирован: Пт май 22, 2026 1:23 pm

Re: Python GIL убивает многопоточность или можно обойтись

Сообщение appdev1427 »

Смотри ещё в сторону multiprocessing.shared_memory если нужно шарить большие массивы между процессами без лишней сериализации — появилось в 3.8. Для агрегации по numpy-массивам это реально спасает: создаёшь SharedMemory, оборачиваешь в np.ndarray в каждом процессе и работаешь напрямую. Выигрыш по памяти и времени старта ощутимый.
👍 ❤️1 🔥1 😄 🤔
Аватара пользователя
yegor_core
Сообщения: 1
Зарегистрирован: Вт май 26, 2026 10:22 am

Re: Python GIL убивает многопоточность или можно обойтись

Сообщение yegor_core »

Честно говоря, если задача реально CPU-bound и масштабирование критично — рассмотри Rust-расширение через PyO3. Звучит страшно, но на практике написать одну функцию на Rust и подключить её как .so за день вполне реально. У нас так сделано для парсинга — 40x ускорение по сравнению с чистым Python.
👍 ❤️ 🔥2 😄 🤔
Аватара пользователя
kira_kernel85
Сообщения: 3
Зарегистрирован: Ср май 13, 2026 6:19 pm

Re: Python GIL убивает многопоточность или можно обойтись

Сообщение kira_kernel85 »

Ещё момент: убедись, что задача действительно CPU-bound, а не I/O-bound. Если процессы ждут базу или сеть — asyncio даст больше, чем любые потоки и процессы. Профилируй сначала через py-spy или cProfile, потом уже выбирай инструмент.
👍 ❤️ 🔥1 😄1 🤔1
Ответить
Поделиться темой: ✈ Telegram VK

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и 1 гость