如何从Python脚本捕获Python解释器和/或CMD.EXE的输出?

  1. 是否有可能从Python脚本捕获Python解释器的输出?
  2. 是否有可能从Python脚本捕获Windows CMD的输出?

如果是这样,我应该看哪个图书馆?

如果你正在谈论的是Python脚本解释器或CMD.exe,那么你的脚本的“父”,那么不行,这是不可能的。 在每一个类似POSIX的系统中(现在你正在运行Windows,看来,这可能有一些我不知道的怪癖,YMMV)每个进程有三个流,标准输入,标准输出和标准错误。 Bu默认值(当在控制台中运行时)这些指向控制台,但可以使用管道符号重定向:

python script_a.py | python script_b.py 

这将脚本a的标准输出流绑定到脚本B的标准输入流。在本例中,标准错误仍然继续到控制台。 请参阅维基百科上关于标准流的文章。

如果你正在谈论一个子进程,你可以像这样从Python启动它(如果你想双向通信,stdin也是一个选项):

 import subprocess # Of course you can open things other than python here :) process = subprocess.Popen(["python", "main.py"], stdout=subprocess.PIPE, stderr=subprocess.PIPE) x = process.stderr.readline() y = process.stdout.readline() process.wait() 

有关管理进程的信息,请参阅Python 子进程模块。 对于通信,process.stdin和process.stdout管道被视为标准文件对象 。

为了使用管道,从标准输入阅读lassevk建议你做这样的事情:

 import sys x = sys.stderr.readline() y = sys.stdin.readline() 

sys.stdin和sys.stdout是上面提到的标准文件对象,在sys模块中定义。 你可能也想看看管道模块。

用readline()读取数据就像在我的例子中是一个非常天真的获取数据的方式。 如果输出不是面向行或不确定的,你可能想看看不幸的是在窗口不工作的投票 ,但我敢肯定,有一些替代方案。

我想我可以指出你的问题的第一部分的一个很好的答案。

1.是否有可能从Python脚本捕获Python解释器的输出?

答案是肯定的 ,我个人喜欢从PEP 343的例子– “带有”声明文件中解脱出来。

 from contextlib import contextmanager import sys @contextmanager def stdout_redirected(new_stdout): saved_stdout = sys.stdout sys.stdout = new_stdout try: yield None finally: sys.stdout.close() sys.stdout = saved_stdout 

像这样使用:

 with stdout_redirected(open("filename.txt", "w")): print "Hello world" 

它的一个很好的方面是它可以有选择地围绕脚本执行的一部分,而不是整个范围,即使在其上下文中引发了未处理的异常时也可以保持有效。 如果您在第一次使用后以附加模式重新打开该文件,则可以将结果累积到一个文件中:

 with stdout_redirected(open("filename.txt", "w")): print "Hello world" print "screen only output again" with stdout_redirected(open("filename.txt", "a")): print "Hello world2" 

当然,上面也可以扩展到将sys.stderr重定向到相同或另一个文件。 另请参阅相关问题的答案 。

其实,你一定可以,同时也是美丽,丑陋,疯狂!

您可以用收集输出的StringIO对象替换sys.stdout和sys.stderr。

下面是一个例子,保存为evil.py:

 import sys import StringIO s = StringIO.StringIO() sys.stdout = s print "hey, this isn't going to stdout at all!" print "where is it ?" sys.stderr.write('It actually went to a StringIO object, I will show you now:\n') sys.stderr.write(s.getvalue()) 

当你运行这个程序时,你会看到:

  • 没有什么去标准输出(打印通常打印到)
  • 写入stderr的第一个字符串是以“It”开头的字符串,
  • 接下来的两行是在StringIO对象中收集的行

像这样替换sys.stdout / err是一个叫做monkeypatching的应用程序。 不管这个“支持”是什么,意见可能会有所不同,这绝对是一个丑陋的黑客,但是当试图围绕外部的东西一两次时,它保存了我的培根。

在Linux上测试,而不是在Windows上,但它应该也是一样的。 让我知道,如果它在Windows上工作!

你想要子进程 。 在17.1.1中特别注意Popen,并在17.1.2中进行交流。

你在哪个环境中问?

你是否试图捕获从命令行启动的程序的输出?

如果是这样,那么这是如何执行它:

 somescript.py | your-capture-program-here 

并读取输出,只需从标准输入读取。

另一方面,如果您正在执行该脚本或cmd.exe或类似程序中的内容,并希望等到脚本/程序完成并捕获其所有输出,则需要查看库调用你用来启动外部程序,很可能有办法让它给你一些方法来读取输出并等待完成。