如何自动加载保存在不同目录和子目录中的所有模块?
我看到这个answer正在使用__import__
,但它仍然不是我想到的自动加载。
我在想与PHP autoloader类似的东西。甚至比Composer autoloader更好。
从目前为止我收集的研究看起来自动加载器在Python中并不是一个流行的东西(不能确定,因为我是Python的新手)。自动加载Python中不鼓励的东西吗?
到目前为止,我的自动加载代码
import os
import sys
root = os.path.dirname(__file__)
sys.path.append(root + "/modules")
sys.path.append(root + "/modules/User")
sys.path.append(root + "/modules/Article")
# IMPORTS MODULES
module = __import__("HelloWorld")
my_class = getattr(module, "HelloWorld")
# This is our application object. It could have any name,
# except when using mod_wsgi where it must be "application"
def application(environ, start_response):
results = []
helloWorld = my_class()
results.append(helloWorld.sayHello())
output = "<br/>".join(results)
print output
...
正如您所看到的,我仍然需要这些行来加载模块,
sys.path.append(root + "/modules")
sys.path.append(root + "/modules/User")
sys.path.append(root + "/modules/Article")
如果我有大量的文件夹和子文件夹怎么办?我要列出所有这些吗?它最终会列出很长的名单,不是吗?
此外,使用__import__
似乎并没有太大的区别,
import os
import sys
root = os.path.dirname(__file__)
sys.path.append(root + "/modules")
sys.path.append(root + "/modules/User")
sys.path.append(root + "/modules/Article")
# IMPORTS MODULES
import hello
import HelloWorld
from HelloWorld import HelloWorld
# This is our application object. It could have any name,
# except when using mod_wsgi where it must be "application"
def application(environ, start_response):
后者看起来更好,更整洁。
有什么想法吗?
答案 0 :(得分:7)
我只是重复@ bruno&#34;不要这样做&#34;。它不值得,但我想补充一下原因:
自动加载Python中不鼓励的东西吗?
在PHP中进行自动加载的一个很好的理由是每次加载某个页面时都会从头开始执行PHP脚本。可以缓存操作码并且文件可能已经准备好,但主要观点仍然是 - 导入另一个文件实际上意味着确保其内容已加载。
这不是Python webservices的工作方式。您的文件不会每次都重读,如果您导入了某些内容,它会在应用的生命周期内保持导入状态。在Python中使用自动加载器没有意义,因为它们只会被使用一次,而不是每次请求都使用。
因此,PHP中的自动加载器可能会为您提供在不需要的情况下跳过文件加载成本的好处。在Python中,您只需在应用程序启动时加载内容。新请求不需要加载任何额外的内容。
答案 1 :(得分:4)
TL; DR:忘了它并使用显式导入。
更长的答案:
Python不是PHP - 既不是技术POV,也不是设计/哲学POV。
Python的哲学部分(又名&#34; Python's Zen&#34;)&#34;显性优于隐式&#34;,&#34;可读性计数&#34; ,和&#34;面对模棱两可,拒绝猜测的诱惑&#34; - 这是一个&#34;功能&#34;像PHP&#34; autoload&#34;高度unpythonic,1。它的方式不如导入mymodule&#34;或者&#34;来自mymodule import SomeName&#34;,2。它的可读性也较低(你不清楚从哪里导入名称),以及3.当两个或多个模块定义时一个相同的名称(这在Python中是完全有效且很常见的),它必须尝试猜测你想要哪一个(这在技术上是不可能的)。
从技术POV中,您无法以可靠的方式在Python 中实现此类功能 - 请参阅上面的第3点。虽然PHP的require
语句和Python的import
语句可能看起来相似,但它们确实以完全不同的方式工作,并且&#34;执行模型&#34;也完全不同。
答案 2 :(得分:1)
以PHP的方式重新加载自动源代码在Python中并不实用。我建议你去看看:
如果你真的必须要有东西,请参阅自动代码重新加载器的详细信息,你可以使用mod_wsgi。切勿在生产系统上使用它。
如果你正在开发,你坦率地说使用mod_wsgi-express可能会更好。参见:
mod_wsgi-express之一就是--reload-on-changes
选项,它为您实现自动代码重新加载。