Как убить процесс и дочерние процессы из Python?
Например из bash:
os.kill(pid, signal.SIGKILL) убить только родительский процесс.
5 ответов
Когда вы передаете отрицательный PID kill , он фактически отправляет сигнал процессу group по этому (абсолютному) номеру. Вы делаете эквивалент с os.killpg() в Python.
Другое решение, если ваш процесс не является группой процессов и вы не хотите использовать psutil , это выполнить команду оболочки:
Ни один из ответов не помог мне, поэтому я провел небольшое исследование и написал свой ответ: Вы можете легко сделать это, используя модуль os , но он чувствителен к платформе. Это означает, что некоторые команды доступны только в Unix, некоторые — на любой платформе. Поэтому мой проект запускает один процесс и несколько дочерних процессов в разных местах и времени. Some of Child запускает процессы Grand-Child 🙂 Итак, я нашел это решение:
Я использую SIGKILL в Linux, чтобы немедленно завершить процесс, и SIGTERM в Windows, потому что там нет SIGKILL . Также я использовал killpg() для уничтожения всей группы процессов в Linux.
Постскриптум Проверьте в Linux, но все еще не проверяете в Windows, поэтому, возможно, нам понадобится еще одна дополнительная команда для Windows (например, CTRL_C_EVENT или используйте другой ответ ).
Если родительский процесс не является «группой процессов», но вы хотите уничтожить его с помощью детей, вы можете использовать psutil (https://pythonhosted.org/psutil/#processes ) . os.killpg не может идентифицировать pid группы, не относящейся к процессу.
Вы должны использовать параметр сигнала 9, чтобы убить дерево процессов.
Завершение программы в Python
Как сделать раннее завершение программы в Python? В самоучителе я нашёл несколько примеров:
Однако там не было объяснения какой метод лучше. Какой метод является наиболее «безаварийным»?
И заодно: есть ли в Python понятие Autocloseable объектов? Если я сделаю ранее завершение программы, нужно ли мне будет закрывать файлы и т.д.?
2 ответа 2
Короткий ответ:
Лучше использовать sys.exit()
Механизм завершения процесса в Python реализован через бросание исключения SystemExit , таким образом можно просто создать подобное исключение и программа завершится:
Функция exit и аналогичная ей quit созданы для удобства работы в интерактивном режиме и их не рекомендуется использовать внутри скриптов:
They are useful for the interactive interpreter shell and should not be used in programs.
По факту они также просто поднимают исключение, и при попытке вызова без скобок напишут подсказку о правильном способе выхода из интерпретатора:
Использовать sys.exit стоит потому, что эта функция лежит в стандартном модуле и будет всегда там доступна. Также это довольно явный способ выразить своё желание завершить программу.
Есть также дополнительный метод для немедленного завершения программы: os._exit . У него довольно специфическая область применения, и там же есть замечание:
The standard way to exit is sys.exit(n)
Т.е. здесь даётся подтверждение того, что стандартный способ завершения программы — это вызов sys.exit .
Функция os.abort , упомянутая вами, использует механизм сигналов процессу. Конкретно при вызове этой функции будет передан сигнал SIGABRT , что в linux приведёт к завершению программы и созданию дампа памяти процесса. Подобное завершение рассматривается операционной системой как аварийное, поэтому не стоит использовать его для безаварийного завершения приложения.
По второй части вопроса. В Python есть развитая система контекстных менеджеров: классов, которые умеют работать с оператором with . Самое частое использование этого механизма встречается, вероятно, с файлами.
Этот код откроет файл, напечатает его содержимое на экран и закроет файл автоматически, даже если возникнет исключение при его печати.
Для классов, которые не приспособлены для работы с with есть функция closing в библиотеке contextlib . Из документации:
is equivalent to this:
Вот небольшой пример работы этой функции:
Теперь небольшое отступление о том, почему стоит использовать конструкцию with .
Известно, что программа завершится от любого необработанного исключения, а не только от SystemExit . Таким образом, если в вашем коде используются какие-то ресурсы, которые требуется правильным образом закрывать перед завершением работы, нужно оборачивать работу с ними в блоки try . finally . .
Однако, при использовании конструкции with это оборачивание происходит автоматически, и все ресурсы закрываются корректно.
Так как выход из программы — это всего лишь брошенное исключение, то и в случае использования функции sys.exit закрытие открытых в операторе with ресурсов произойдёт корректно:
Вы можете писать также и свои классы, предоставляющие ресурсы или классы, оборачивающие другие, которые нужно уметь закрывать автоматически. Для этого используются методы __enter__ и __exit__ .
Убить процесс в python
Здравствуйте, уважаемые форумчане. Просьба помочь. Имеются две кнопки. По нажатию на первую срабатывает функция запуска процеcса:
Работает нормально. Теперь нужно, чтобы после нажатия другой кнопки процесс завершался и консоль закрывалась. Но не работает(((
В твоей предыдущей теме:
Если бы я понял, как это сделать, то не спрашивал бы
не работает. в случае процесс даже не запускается
УМВР, давай весь код.
В первом сообщении и есть основной код. Первая ф-ция работает норм, т.е. консоль открывается и процесс запускается. а вторая не работает
В первом сообщении и есть основной код.
Почитай про пространства имён. Судя по всему, ты пытаешься грохнуть несуществующий процесс. Поэтому у тебя и «не работает».
Потому что proc из первой функции и proc из второй — это две разных переменных?
В смысле если в on_task_close заменить proc.kill() на proc.terminate() то процесс не запускается? Он ведь у тебя в другой функции запускается.
и с тем и другим не запускается
Так а если глобальной ее сделать??
P.S. импорты полагается делать в начале файла, а не в теле функции. И зачем делать «from subprocess import Popen, PIPE» если до этого уже сделал «import subprocess»?
Так всё-таки «Первая ф-ция работает норм, т.е. консоль открывается и процесс запускается. а вторая не работает» или «и с тем и другим не запускается»?
Ну вот ты сделал её глобальной в первой функции, и при этом пытаешься во второй работать с локальной как с глобальной. Ну и что тебе это дало, кроме неработающего кода?
Вот с этим все таки запускается: proc.kill()
Но пишет ошибку NameError: name ‘proc’ is not defined
хотя я объявил global proc
Но пишет ошибку NameError: name ‘proc’ is not defined
Ещё раз: Почитай про пространства имён.
Если присваивание производится за пределами всех инструкций def, она является глобальной для всего файла.
я так и делаю. а он говорит не определено((
Почему у меня после вызова f2() переменная содержит значение ‘test 1’?
Потому что после вызова f1() a = ‘test 1’ стала глобальной
В этом случае у меня даже не запускается((
Почему тогда после вызова f2() переменная глобальная переменная «a» не приняла значение «test 2»?
Потому что она объявлена глобальной внутри f1() и, следовательно, именно это значение переменной «a» мы можем получить в других функциях
В этом случае у меня даже не запускается((
Что значит, «не запускается»? Ошибка происходит?
proc = subprocess.Popen(«konsole -workdir » + full_dir + » -e bash /*/*/OpenFOAM/QW», shell=True)
Ты, может быть, имел в виду «konsole -workdir » + full_dir + » -e ‘bash /*/*/OpenFOAM/QW'» #Экранирован параметр к -e
Или, может быть, subprocess.Popen([‘konsole’, ‘-workdir’, full_dir, ‘-e’, ‘bash /*/*/OpenFOAM/QW’]) ?
Блин, ты так хитро запутался что я даже не знаю как тебя распутать. Лучшее что могу посоветовать это забыть всё что ты знаешь об областях видимости переменных и прочесть о том как оно на самом деле.
Что с ходу нагуглилось https://ru.wikibooks.org/wiki/Python/Учебник_Python_3.1#.D0.9E.D0.B1.D0.BB.D0.
Но перед тем всё-же можешь подумать почему функция f1() обращается к глобальной переменной «a», а f2() к локальной.
и с тем и другим не запускается
Судя по всему, ты пытаешься грохнуть несуществующий процесс. Поэтому у тебя и «не работает».
Потому что proc из первой функции и proc из второй — это две разных переменных?
Я не понял, в питоне что нельзя вывести ероры и варнинги в консоль куда-нибудь?
Если будет ошибка — сразу понятно что случилось.
К примеру: variable is not defined
И тогда человек знает, ок, почему это не определена, и далее курит про пространство имет и т.п.
Народ, а нас случаем не внесут в реестр за такую провакационную тему как убийство?
Смотри Убить процесс в python (комментарий)
Топикстартер завис где-то между шагами «увидеть variable is not defined» и «курить про пространство имен»
оу, кажется я пропустил этот пост
П.С. звиняйте, нажрался. Наверное пора закрывать на сегодня вкладку с ЛОР
Как остановить /прекратить запуск скрипта Python?
Я написал программу в IDLE для токенизации текстовых файлов, и она начала токенизировать 349 текстовых файлов! Как я могу это остановить? Как я могу остановить работающую программу на Python?
12 ответов
Чтобы остановить вашу программу, просто нажмите Control + C .
Вы также можете сделать это, если используете в своем коде функцию exit() . В идеале вы можете сделать sys.exit() . sys.exit() может завершить работу Python, даже если вы запускаете вещи параллельно через multiprocessing пакет.
Ctrl-Break он более мощный, чем Ctrl-C
- Чтобы остановить скрипт Python, просто нажмите Ctrl + C .
- Внутри скрипта с exit() вы можете сделать это.
- Вы можете сделать это в интерактивном скрипте, просто выйдя.
- Вы можете использовать pkill -f name-of-the-python-script .
Чтобы остановить работающую программу: используйте CTRL + C, чтобы завершить процесс.
Чтобы обработать это программно в python: импортируйте модуль sys и используйте sys.exit там, где вы хотите прекратить программу.
Если ваша программа работает на интерактивной консоли, нажатие CTRL + C вызовет KeyboardInterrupt исключение в главном потоке.
Если ваша программа на Python ее не перехватит, KeyboardInterrupt приведет к выходу Python. Однако, блок except KeyboardInterrupt: или что-то наподобие except: , будет препятствовать тому, чтобы этот механизм фактически останавливал выполнение сценария.
Иногда, если KeyboardInterrupt не работает, вы можете отправить SIGBREAK вместо; в Windows интерпретатор может обрабатывать CTRL + Pause /Break без генерации перехватываемого KeyboardInterrupt исключение.
Однако эти механизмы в основном работают, только если интерпретатор Python работает и отвечает на события операционной системы. Если интерпретатор Python по какой-либо причине не отвечает, наиболее эффективным способом является завершение всего процесса операционной системы, на котором выполняется интерпретатор. Механизм этого зависит от операционной системы.
В среде оболочки в стиле Unix вы можете нажать CTRL + Z , чтобы приостановить любой процесс, который в данный момент контролирует консоль. После того, как вы вернете приглашение оболочки, вы можете использовать jobs , чтобы вывести список приостановленных заданий, и вы можете убить первое приостановленное задание с помощью kill %1 . (Если вы хотите запустить его снова, вы можете продолжить работу на переднем плане, используя fg %1 ; прочитайте руководство вашей оболочки по управлению заданиями для получения дополнительной информации.)
Кроме того, в Unix или Unix-подобной среде вы можете найти PID (идентификатор процесса) процесса Python и уничтожить его с помощью PID. Используйте что-то вроде ps aux | grep python , чтобы найти запущенные процессы Python, а затем используйте kill
для отправки сигнала SIGTERM .
Команда kill в Unix отправляет SIGTERM по умолчанию, и программа Python может установить обработчик сигнала для SIGTERM , используя signal модуль. Теоретически, любой обработчик сигнала для SIGTERM должен корректно завершить процесс. Но иногда, если процесс застрял (например, заблокирован в состоянии непрерывного ожидания ввода-вывода), сигнал SIGTERM не действует, потому что процесс не могу даже проснуться, чтобы справиться с этим.
Чтобы принудительно завершить процесс, который не отвечает на сигналы, необходимо отправить сигнал SIGKILL , иногда называемый —- +: = 20 =: + —-, потому что kill -9 является числовым значением 9 константа. Из командной строки вы можете использовать SIGKILL (или kill -KILL
Обзор процесса Pythonw.exe
Существует множество языков программирования, которые используются для написания разного рода приложений. Если не вдаваться в технические подробности, то для работы каждой программы нужны библиотеки с ресурсами и фреймворками того языка разработки, на котором был создан софт. Поэтому рассмотрим, что это за процесс Pythonw.exe и как его остановить.
Что такое Pythonw.exe?
Pythonw.exe (Run Python without a terminal window) – это интерпретатор для языка программирования Python. Если вы обнаружили данный процесс в Диспетчере задач – значит на машине работает приложение, использующее Python Software Foundation.
Сам по себе файл не представляет опасности, он просто выполняет инструкции и служит площадкой для выполнения кода. А вот скрипты и тулы, которые он запускает, могут содержать в себе киберугрозу. Это приведет к замедлению работы компьютера, появлению агрессивной рекламы, возникновению критических ошибок и в самых тяжелых случаях повреждение системы и личных данных.
Удаление или отключение Pythonw.exe никак не влияет на производительность и работу ОС. У файла высокий технический рейтинг опасности (47%), размер 27,136 (75% случаев) или 27,648 байт. Информации о MD5 и SHA-1 нет. Если вышеописанные характеристики не совпадают со значениями вашего файла – pythonw.exe был поврежден или заражен вирусом.
Как остановить процесс и исправить ошибку?
Ниже представлена инструкция по удалению файла pythonw.exe. Если он в будущем будет нужен, использующие его приложения самостоятельно распакуют или загрузят недостающие объекты. Поэтому, желая избавиться от ошибки, просто удалите старый файл и пользуйтесь программами дальше. Они сами подскажут, что от вас требуется.
Итак, для остановки и удаления процесса выполните следующее:
- Вызовите «Диспетчер задач» путем зажатия Ctrl+Shift+Esc.
- Найдите pythonw.exe и принудительно остановите процесс.
- Нажмите Win+R и вызовите окно «Выполнить».
- Введите cmd в текстовое поле и нажмите Enter.
- В окне командной строки напечатайте sc delete pythonw.exe и нажмите Enter.
- Дождитесь завершения операции и закройте окно.