我正在研究pypreprocessor,这是一个接受c风格指令的预处理器,我已经能够使它像传统的预处理器一样工作(它是自用的,并且可以动态执行后处理代码),只是它中断了库导入。
问题是:预处理器在文件中运行,处理它,输出到临时文件,然后exec()临时文件。导入的库需要进行一些不同的处理,因为它们不会被执行,而是被加载并可供调用方模块访问。
我需要做的是:中断导入(因为预处理器正在导入的中间运行),将后处理代码加载为tempModule,并用tempModule替换原始导入,以诱使调用脚本相信tempModule是原始模块。
我到处都找了,到目前为止还没有找到解决办法。
这个堆栈溢出问题是迄今为止我看到的最接近于提供答案的问题: Override namespace in Python
这是我有的。
# Remove the bytecode file created by the first import
os.remove(moduleName + '.pyc')
# Remove the first import
del sys.modules[moduleName]
# Import the postprocessed module
tmpModule = __import__(tmpModuleName)
# Set first module's reference to point to the preprocessed module
sys.modules[moduleName] = tmpModule
module name是原始模块的名称,tmpModuleName是后处理代码文件的名称。
奇怪的是,这个解决方案仍然完全正常运行,就像第一个模块正常完成加载一样;除非删除最后一行,否则会出现模块未找到错误。
希望Stack Overflow上的人比我更了解导入,因为这个让我难堪。
注意:我只授予一个解决方案,或者,如果在Python中这是不可能的,则授予一个最好的、最详细的解释,解释为什么这不是不可能的。
更新:对于任何感兴趣的人,这里是工作代码。
if imp.lock_held() is True:
del sys.modules[moduleName]
sys.modules[tmpModuleName] = __import__(tmpModuleName)
sys.modules[moduleName] = __import__(tmpModuleName)
“imp.lock\u hold”部分检测模块是否作为库加载。其余的行由下面的行来完成。
要定义不同的导入行为或完全颠覆导入过程,您需要编写导入挂钩。见PEP 302。
例如
它输出:
所以基本上它返回一个新的模块(可以是任何对象),在本例中就是这样。您可以使用它在导入
xxx
时返回processe_xxx
,从而更改导入行为。IMO:Python不需要预处理器。由于Python本身的动态特性,您正在完成的任何事情都可以在Python中完成,例如,以debug为例,在文件顶部设置
后来
是吗?
这能回答你的问题吗?第二次进口就成功了。
模型1.py
模型2.py
测试.py
在Python 2中有一个^{} 模块,它似乎提供了您正在寻找的功能,但是在Python 3中已经被删除了。它没有很好的文档记录,但是包含一个示例部分,展示了如何替换标准导入函数。
对于Python 3,有一个^{} 模块(在python3.1中引入),它包含以各种方式修改导入功能的函数和类。它应该适合将预处理器挂接到导入系统中。
相关问题 更多 >
编程相关推荐