Існує кілька реалізацій Python, наприклад, CPython, IronPython, RPython тощо.
Деякі з них мають GIL, деякі - ні. Наприклад, CPython має GIL:
З http://en.wikipedia.org/wiki/Global_Interpreter_Lock
Програми, написані на мовах програмування з GIL, можуть бути розроблені для використання окремих процесів для досягнення повного паралелізму, оскільки кожен процес має власного перекладача і, в свою чергу, має власний GIL.
Переваги GIL
- Збільшена швидкість однопотокових програм.
- Проста інтеграція бібліотек C, які зазвичай не є безпечними для потоків.
Чому Python (CPython та інші) використовує GIL
У CPython глобальне блокування інтерпретатора або GIL - це мютекс, який запобігає виконанню декількох нативних потоків одночасно байт-кодами Python. Цей замок необхідний головним чином, оскільки управління пам'яттю CPython не є безпечним для потоків.
GIL є суперечливим, оскільки він заважає багатопоточним програмам CPython повною мірою використовувати переваги багатопроцесорних систем у певних ситуаціях. Зауважте, що потенційно блокуючі або тривалі операції, такі як введення / виведення, обробка зображення та стиснення числа NumPy, відбуваються поза GIL. Тому лише у багатопотокових програмах, які проводять багато часу всередині GIL, інтерпретуючи байт-код CPython, GIL стає вузьким місцем.
У Python є GIL на відміну від дрібнозернистого блокування з кількох причин:
Це швидше в однонитковому корпусі.
Це швидше в багатопотоковому випадку для програм зв'язаного вводу / виводу.
Це швидше в багатопотоковому випадку для програм, пов'язаних з процесором, які виконують обчислювальну роботу в бібліотеках С.
Це полегшує запис розширень на C: не буде перемикання потоків Python, за винятком випадків, коли ви дозволяєте це статися (тобто між макросами Py_BEGIN_ALLOW_THREADS та Py_END_ALLOW_THREADS).
Це спрощує обгортання бібліотек C. Вам не доведеться турбуватися про безпеку ниток. Якщо бібліотека не є безпечною для потоків, ви просто тримаєте GIL заблокованим, поки ви її викликаєте.
GIL може бути випущений розширеннями C. Стандартна бібліотека Python вивільняє GIL навколо кожного блокуючого дзвінка вводу / виводу. Таким чином, GIL не має наслідків для роботи серверів, пов'язаних введенням / виводу. Таким чином, ви можете створювати мережеві сервери в Python, використовуючи процеси (fork), потоки або асинхронний введення-виведення, і GIL не заважатиме.
Числові бібліотеки в С або Фортран можна аналогічно назвати із звільненим GIL. Поки ваше розширення C очікує завершення FFT, інтерпретатор виконує інші потоки Python. Таким чином, GIL є простішим та швидшим, ніж дрібнозернисте блокування і в цьому випадку. Це складає основну частину чисельної роботи. Розширення NumPy випускає GIL, коли це можливо.
Нитки зазвичай є поганим способом написання більшості серверних програм. Якщо навантаження низька, розгортання легше. Якщо навантаження велика, краще асинхронне введення / виведення та програмування на основі подій (наприклад, використання Twisted Framework Python). Єдиним приводом для використання потоків є відсутність os.fork у Windows.
GIL - це проблема, якщо і лише тоді, коли ви робите інтенсивну роботу процесора в чистому Python. Тут ви можете отримати більш чіткий дизайн за допомогою процесів і передачі повідомлень (наприклад, mpi4py). Також у сирному цеху Python є модуль "обробки", який надає процесам той самий інтерфейс, що і потоки (тобто замінює нарізання. Thread на обработку.Process).
Нитки можна використовувати для підтримки чутливості графічного інтерфейсу незалежно від GIL. Якщо GIL погіршує вашу ефективність (див. Обговорення вище), ви можете дозволити вашому потоку породити процес і чекати, коли він закінчиться.