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

В чем разница между spawn и fork?

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

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

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

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

Различия между spawn и fork

Это два разных метода создания процессов в Python. Они кардинально отличаются тем, как они инициализируют новый процесс и как работают с памятью.

fork — копирование процесса (UNIX/Linux)

Назначение: fork создаёт точную копию текущего процесса, включая всё его состояние (переменные, открытые файлы, стек и т.д.).

import os
import time

def parent_process():
    print(f"Parent process ID: {os.getpid()}")
    
    # Создание дочернего процесса
    child_pid = os.fork()
    
    if child_pid == 0:
        # Мы в дочернем процессе
        print(f"Child process ID: {os.getpid()}")
        print(f"Parent of child: {os.getppid()}")
        time.sleep(2)
        print("Child process finished")
        os._exit(0)
    else:
        # Мы в родительском процессе
        print(f"Created child with PID: {child_pid}")
        os.waitpid(child_pid, 0)  # Ждём завершения дочернего процесса
        print("Parent process finished")

if __name__ == "__main__":
    parent_process()

Ключевые характеристики:

  • Очень быстрое создание (всего копирование памяти)
  • Полная копия состояния родительского процесса
  • Дочерний процесс имеет отдельное адресное пространство памяти
  • Доступен только на UNIX/Linux (не на Windows)
  • Все переменные копируются, но изменения в дочернем процессе не влияют на родителя

spawn — запуск нового процесса (кроссплатформенный)

Назначение: spawn запускает совершенно новый процесс с чистым состоянием. Ничего не копируется — всё инициализируется заново.

from multiprocessing import Process
import os

def child_function(name):
    print(f"Child process ID: {os.getpid()}")
    print(f"Hello from {name}")

if __name__ == "__main__":
    print(f"Parent process ID: {os.getpid()}")
    
    # Создание нового процесса через spawn
    p = Process(target=child_function, args=("child_1",))
    p.start()
    p.join()  # Ждём завершения
    
    print("Parent finished")

Ключевые характеристики:

  • Медленнее, чем fork (нужна полная инициализация Python интерпретатора)
  • Новый процесс запускается с пустым состоянием
  • Данные передаются явно через аргументы функции
  • Работает на всех платформах (Windows, Linux, macOS)
  • Безопаснее (меньше вероятность deadlock'ов)

Таблица сравнения

Параметрforkspawn
СкоростьОчень быстроМедленнее
Копирование состоянияПолноеНет
ПамятьИспользует Copy-on-WriteОтдельное пространство
ПлатформыТолько UNIX/LinuxВсе платформы
Передача данныхАвтоматически (копия)Явно через аргументы
БезопасностьРискованнееБезопаснее

Практические примеры

fork (только Linux):

import os
import multiprocessing

# Явно указываем fork
if hasattr(multiprocessing, 'set_start_method'):
    try:
        multiprocessing.set_start_method('fork')
    except RuntimeError:
        pass  # Уже установлена

from multiprocessing import Pool

def process_item(x):
    return x * 2

if __name__ == "__main__":
    with Pool(processes=4) as pool:
        results = pool.map(process_item, range(10))
    print(results)

spawn (универсальный):

import multiprocessing

if hasattr(multiprocessing, 'set_start_method'):
    multiprocessing.set_start_method('spawn', force=True)

from multiprocessing import Queue, Process

def worker(queue):
    queue.put("Result from child")

if __name__ == "__main__":
    q = Queue()
    p = Process(target=worker, args=(q,))
    p.start()
    result = q.get()
    p.join()
    print(result)

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

fork:

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

spawn:

  • Кроссплатформенность (Windows, Linux, macOS)
  • Безопасность и предсказуемость
  • Когда работаете с потоками в родительском процессе
  • Когда нужна явная передача данных

Вывод

fork — быстро, но только UNIX (и рискованнее)

spawn — безопаснее и кроссплатформенно (стандарт для Python 3.14+)

В чем разница между spawn и fork? | PrepBro