Python как сделать так, чтобы скрипт ping -t выполнялся бесконечно

#python #python-3.x #cmd #windows-10 #subprocess

#python #python-3.x #cmd #windows-10 #подпроцесс

Вопрос:

Я хочу запустить файл скрипта python с помощью этой ping -t www.google.com команды.

До сих пор я делал это с ping www.google.com помощью команды, которая работает, но мне не удалось выполнить ping -t цикл бесконечно.

Ниже вы можете найти мой ping.py скрипт:

 import subprocess

my_command="ping www.google.com"
my_process=subprocess.Popen(my_command, stdout=subprocess.PIPE, stderr=subprocess.PIPE)

result, error = my_process.communicate()
result = result.strip()
error = error.strip()

print ("nResult of ping commandn")
print("-" *22)
print(result.decode('utf-8'))
print(error.decode('utf-8'))
print("-" *22)
input("Press Enter to finish...")
  

Я хочу, чтобы командное окно оставалось открытым после завершения. Я использую Python 3.7.

Комментарии:

1. while True не сработало?

2. Не выполняйте пинг из подпроцесса, это нонсенс. Существуют собственные модули Python, которые реализуют протокол ICMP, выберите один из них.

3. @Tomalak Я новичок в Python, извините, какой модуль я могу использовать вместо этого? Я буду рад узнать.

Ответ №1:

Если вы хотите сохранить процесс открытым и постоянно взаимодействовать с ним, вы можете использовать my_process.stdout в качестве входных данных и, например, выполнять итерации по его строкам. С помощью «communicate» вы ждете, пока процесс не завершится, что было бы плохо для бесконечно запущенного процесса 🙂

 import subprocess

my_command=["ping", "www.google.com"]
my_process=subprocess.Popen(my_command, stdout=subprocess.PIPE, stderr=subprocess.PIPE)

while True:
    print( my_process.stdout.readline() )
  

Редактировать

В этой версии мы используем re только для получения части «time = xxms» из выходных данных:

 import subprocess
import re

my_command=["ping", "-t", "www.google.com"]
my_process=subprocess.Popen(my_command, stdout=subprocess.PIPE, 
stderr=subprocess.PIPE)

while True:
    line = my_process.stdout.readline() #read a line - one ping in this case
    line = line.decode("utf-8") #decode the byte literal to string
    line = re.sub("(?s).*?(time=.*ms).*", "\1", line) #find time=xxms in the string and use only that

    print(line)
  

Комментарии:

1. Кажется, это работает при использовании ping , но сбой при попытке с ping -t

2. В настоящее время я не могу протестировать с Windows, с Linux все работает нормально. Что вы пробовали в качестве «my_command»? Это должно выглядеть так: my_command=[«ping», «-t», «www.google.com «] (каждая часть команды как отдельная запись в списке.

3.Вы правы, я использовал его неправильно, спасибо за ваш ответ! кстати, вывод в настоящее b'Reply from IP_ADDRESS: bytes=32 time=15ms TTL=54rn' время у вас есть идея, как скрыть как b' в начале, так и rn' в конце? Я не понимаю, почему они здесь. Или даже лучше просто отображать, time=15ms но это другой вопрос.

4. Да, буква «b» впереди указывает на байтовый литерал вместо строки. вы можете декодировать его в строку. Время = xxms можно извлечь с помощью re. Я соответствующим образом обновил свой ответ.