在Google App Engine的Python中,如何捕获print语句产生的输出?

0 投票
2 回答
1534 浏览
提问于 2025-04-15 18:19

我正在使用谷歌应用引擎的环境,想从字符串中加载 doctests 和 Python 代码,以测试 Python 的作业。我的基本实现(由 Alex Martelli 提供)似乎能解决我所有的问题,除了那些包含 print 语句的情况。当我尝试在 GAE 中执行 print 命令时,似乎出现了问题。

你会如何修改这个例子,以捕捉 print 语句输出的内容呢?

#This and most other code works
class X(object): pass

x=X()
exec 'a=23' in vars(x)


#This throws an error. 
class X(object): pass

x=X()
exec 'print 23' in vars(x)

2 个回答

4

对于这个问题,我想直接获取字符串的输出。在你的函数里面,我会使用类似下面的代码:

import StringIO, sys

# create file-like string to capture output
codeOut = StringIO.StringIO()

# capture output and errors
sys.stdout = codeOut
err = ''

try   : 
    exec code in code_namespace
except Exception:
    err = str(sys.exc_info()[1])

最后要加上:
# 恢复标准输出和错误输出
sys.stdout = sys.__stdout__

这样可以让打印功能恢复正常。

5

我觉得Hooked的回答是对的,不过我认为你最好在修改之前先保存一下sys.stdout的值,然后在修改后再把这个值恢复回来,而不是恢复sys.__stdout__。因为(我觉得)App Engine的运行环境会以它自己的方式对sys.stdout进行一些处理。

这样你就可以得到类似下面的代码:

import StringIO
import sys

# Store App Engine's modified stdout so we can restore it later
gae_stdout = sys.stdout

# Redirect stdout to a StringIO object
new_stdout = StringIO.StringIO()
sys.stdout = new_stdout

# Run your code here, however you're doing that

# Get whatever was printed to stdout using the `print` statement (if necessary)
printed = new_stdout.getvalue()

# Restore App Engine's original stdout
sys.stdout = gae_stdout

撰写回答