Ответ 1
Thread.start() никогда не возвращается! Может ли это иметь какое-то отношение к реализации математической библиотеки C?
Как @eryksun указал в комментарии: math.factorial() реализуется как функция C, которая не выпускает GIL, поэтому никакой другой код Python не может работать до тех пор, пока он не вернется.
Примечание. multiprocessing
версия должна работать так: каждый процесс Python имеет свой собственный GIL.
factorial(1000000000)
имеет сотни миллионов цифр. Вместо этого попробуйте import time; time.sleep(10)
как фиктивный расчет.
Если у вас есть проблемы с многопоточным кодом в IDLE, попробуйте тот же код из командной строки, чтобы убедиться, что ошибка сохраняется.
Если p.is_alive()
возвращает False
после того, как p.start()
уже вызван, это может означать, что в f()
есть ошибка, например, MemoryError
.
На моей машине p.is_alive()
возвращает True
, а один из cpus - на 100%, если я вставляю свой код из вопроса в оболочку Python.
Несвязанный: удалить импорт подстановочных знаков, например from multiprocessing import *
. Они могут затенять другие имена в вашем коде, чтобы вы не могли быть уверены в том, что означает определенное имя, например, threading
может определить функцию eval
(она не может это сделать) с аналогичной, но другой семантикой, которая может сломаться ваш код молча.
Я хочу, чтобы моя программа умела корректно обрабатывать смешные входы от пользователя
Если вы передаете пользовательский ввод непосредственно в eval()
, пользователь может сделать что угодно.
Есть ли способ получить процесс для печати, скажем, сообщения об ошибке без создания канала или другой подобной структуры?
Это обычный код Python:
print(message) # works
Разница в том, что если несколько процессов выполняются print()
, тогда выход может быть искажен. Вы можете использовать блокировку для синхронизации вызовов print()
.