← Назад к вопросам

Какие знаешь способы мультипроцессорного выполнения задач?

2.0 Middle🔥 131 комментариев
#Python Core#Асинхронность и многопоточность

Комментарии (1)

🐱
claude-haiku-4.5PrepBro AI22 мар. 2026 г.(ред.)

Ответ сгенерирован нейросетью и может содержать ошибки

Способы мультипроцессорного выполнения задач в Python

В Python существует несколько подходов для параллельного выполнения работ на нескольких процессорных ядрах. Каждый метод имеет свои особенности и область применения.

1. Модуль multiprocessing

Самый прямой способ обхода GIL (Global Interpreter Lock). Создаёт отдельные процессы Python с независимыми интерпретаторами.

from multiprocessing import Process, Pool
import time

def worker(name, delay):
    time.sleep(delay)
    print(f"Worker {name} finished")

# Создание процесса
p = Process(target=worker, args=("A", 2))
p.start()
p.join()

# Pool для управления несколькими процессами
with Pool(processes=4) as pool:
    results = pool.map(worker, [("B", 1), ("C", 2)])

Плюсы: истинный параллелизм, обход GIL, хорошо для CPU-bound задач. Минусы: высокие накладные расходы на создание процесса, сложность обмена данными.

2. Модуль threading

Потоки внутри одного процесса с общей памятью.

from threading import Thread
import time

def threaded_worker(name):
    time.sleep(1)
    print(f"Thread {name} done")

threads = [Thread(target=threaded_worker, args=(f"T{i}",)) for i in range(4)]
for t in threads:
    t.start()
for t in threads:
    t.join()

Плюсы: легко создавать, разделяют память, подходят для I/O-bound задач. Минусы: GIL ограничивает параллелизм CPU, нужна синхронизация.

3. asyncio

Асинхронное программирование для I/O-bound операций на одном потоке.

import asyncio

async def async_task(name, delay):
    await asyncio.sleep(delay)
    print(f"Task {name} done")

async def main():
    await asyncio.gather(
        async_task("A", 1),
        async_task("B", 2),
        async_task("C", 1)
    )

asyncio.run(main())

Плюсы: очень эффективно для I/O, минимум ресурсов, просто масштабируется. Минусы: не работает с CPU-bound, требует async-compatible библиотек.

4. concurrent.futures

Высокоуровневый интерфейс для параллельной работы.

from concurrent.futures import ProcessPoolExecutor, ThreadPoolExecutor

def cpu_intensive(n):
    return sum(i*i for i in range(n))

# Для CPU-bound
with ProcessPoolExecutor(max_workers=4) as executor:
    results = list(executor.map(cpu_intensive, [10**7, 10**7, 10**7]))

# Для I/O-bound
with ThreadPoolExecutor(max_workers=10) as executor:
    futures = [executor.submit(io_task, i) for i in range(10)]
    results = [f.result() for f in futures]

Плюсы: простой API, flexibility в выборе executor'а. Минусы: меньше контроля чем multiprocessing/threading.

5. Распределённые системы

Для действительно крупной масштабируемости используют Celery, RQ, Dask.

from celery import Celery

app = Celery("tasks")

@app.task
def add(x, y):
    return x + y

result = add.delay(4, 6)  # Отправить на worker

Когда что использовать

  • CPU-bound (вычисления): multiprocessing или ProcessPoolExecutor
  • I/O-bound (сеть, файлы): asyncio или ThreadPoolExecutor
  • Масштабирование: Celery, RQ, Dask
  • Простота: concurrent.futures

Выбор зависит от характера задач, количества вычислений и требований к масштабируемости.