sys
模块有两个我感兴趣的全局属性:sys.stdout
和{
我正在构建一个自己的模块,它(除其他外)用自己的包装器替换sys.stdout
和{
_orig_stdout = sys.stdout
_orig_stderr = sys.stderr
sys.stdout = MyFakeStdoutClass()
sys.stderr = MyFaleStderrClass()
这正如预期的那样工作——在导入模块后的任何时候,尝试使用sys.stdout
或{
现在,我的模块有一个既得利益,就是要确保这种安排保持现在的样子——它希望永久地控制sys.stdout
和{sys.stdout
,但我的模块不希望它们这样做。相反,我的模块想拦截他们的企图。在
对于常规类,这样做很容易-我只需覆盖该类的__setattr__()
方法:
但是,我已经尝试为sys
模块本身执行此操作,但是它不起作用(即使在我执行sys.__setattr__ = my_setattr
操作之后,我发现my_setattr
永远不会被调用)。在
另外,虽然other answers指出了为sys
模块创建自己的包装类并将其分配给sys.modules['sys']
的可能解决方案,但这行不通——如果在我的模块被另一个模块导入之前,sys
是在该模块导入我的模块之前导入的,那么我的更改将无法坚持。在
此外,使用一些helper方法设置sys.stdout = property(stdout_getter, stdout_setter)
来返回/修改我的_orig_stdout
变量也不起作用。即使后来在同一个文件中,我也可以只做sys.stdout = sys.__stdout__
,它就恢复正常了。我不想这成为可能。在
有没有一个好办法可以绕过这个限制?在
在python上完全重写stdout的唯一真正方法是实际重写stdout文件描述符(1)。这可以使用^{} 系统调用来完成。在
下面是一个跨平台的例子,展示了如何重写stdout,允许对写入它的所有数据使用自定义逻辑。在这个例子中,逻辑只是复制写入stdout的所有字符。在
运行此示例将输出:
^{pr2}$对于某些版本的python,必须将
PYTHONLEGACYWINDOWSSTDIO
环境变量设置为非空字符串,才能使此示例在windows上运行。在相关问题 更多 >
编程相关推荐