我遇到子流程代码问题。 subprocess.Popen()
工作正常,但当我尝试通过stdout.read()
读取其输出时,没有值可读。
**import os
import signal
import subprocess
import threading
import sys
import commands
print commands.getoutput("hcitool dev")
print 'down'
commands.getoutput('hciconfig hci1 down')
print 'up'
commands.getoutput('hciconfig hci1 up')
commands.getoutput('killall hcitool')
stop = False
ping = subprocess.call('hcitool lescan', shell = False,
stdout=subprocess.PIPE,executable='/bin/bash')
for i in ping.stdout:
print i
def kill():
global stop
stop = True
os.kill(ping.pid, signal.SIGTERM)
threading.Timer(5, kill).start()
#while not stop:
# print 'now in while not loop'
# sys.stdout.write(ping.stdout.read(1))
print 'trying to print stdout'
out, err = ping.communicate()
print "out",out
#result = out.decode()
print "Result : ",result**
当我将hcitool lescan
更改为ping www.google.com并生成输出时,此代码正常工作,但当我尝试使用hcitool lescan
时,它会永久挂起或不产生输出。感谢帮助!
答案 0 :(得分:5)
上述任何一个答案对我都没有用。挂在hcitool的永远扫描。最后我写了一个shell脚本并用我的python代码调用它。这对我来说很好,我正在读取文件" result.txt"的输出。
hcitool lescan>result.txt &
sleep 5
pkill --signal SIGINT hcitool
答案 1 :(得分:0)
您的代码中存在多个错误,例如subprocess.call()
返回一个整数(程序的退出状态),整数没有.stdout
属性;此外,shell=False
和非 - 无executable
的组合很少有用(在这种情况下可能使用不正确)。
修复代码的最简单方法是使用check_output()
:
from subprocess import check_output as qx
output = qx(["hcitool", "lescan"]) # get all output at once
print output,
作为替代方案,您可以在刷新标准输出后立即逐行打印程序的输出:
from subprocess import Popen, PIPE
proc = Popen(["hcitool", "lescan"], stdout=PIPE, bufsize=1) # start process
for line in iter(proc.stdout.readline, b''): # read output line-by-line
print line,
# reached EOF, nothing more to read
proc.communicate() # close `proc.stdout`, wait for child process to terminate
print "Exit status", proc.returncode
要杀死子进程,您可以使用其.kill()
方法,例如:
from threading import Timer
def kill(process):
try:
process.kill()
process.wait() # to avoid zombies
except OSError: # ignore errors
pass
Timer(5, kill, [proc]).start() # kill in 5 seconds
答案 2 :(得分:0)
非常感谢..但问题是hcitool lescan永远不会停止,因此会在代码的下一行中挂起。 我在这里发现了类似的解决方案。这个工作正常,我没有必要杀死子进程,这段代码需要一些额外的时间来输出输出,但是下面这段代码很有效,
from os import kill
import signal
import subprocess
import threading
import tempfile
import sys
import time
from tempfile import TemporaryFile
import commands
t = TemporaryFile()
global pipe_output
print commands.getoutput("hcitool dev")
print 'down'
commands.getoutput('hciconfig hci0 down')
print 'up'
commands.getoutput('hciconfig hci0 up')
print commands.getoutput("hcitool dev")
commands.getoutput('killall hcitool')
p = subprocess.Popen('hcitool lescan', bufsize = 0,shell = True, stdout =subprocess.PIPE,stderr = subprocess.STDOUT)
time.sleep(10)
#os.kill(p.pid,signal.SIGTERM)
for i in range(0,30,1):
print 'for'
inchar = p.stdout.readline()
i+=1
if inchar:
print 'loop num:',i
print str(inchar)
t.write(str(inchar))
print 'out of loop'
t.seek(0)
print t.read()
任何帮助如何减少等待时间,除了更改time.sleep(),表示赞赏 谢谢大家
答案 3 :(得分:0)
使用Popen类而不是调用类。 hcitool lescan将永远运行。 subprocess.call等待调用完成返回。 Popen不等。