Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/300.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python中的自动加载_Python_Coding Style_Autoload - Fatal编程技术网

Python中的自动加载

Python中的自动加载,python,coding-style,autoload,Python,Coding Style,Autoload,在过去,我曾使用perl的自动加载功能实现将符号延迟加载到名称空间中,并希望在python中实现相同的功能 传统上,最接近的方法是使用类和\uu getattr\uuu类来实现这类功能。然而,我也尝试在sys.modules中搜索,并得出以下结论: # mymod.py def greet(greeting="Hello World"): print greeting class autoload(object): def __init__(self, __name__):

在过去,我曾使用perl的自动加载功能实现将符号延迟加载到名称空间中,并希望在python中实现相同的功能

传统上,最接近的方法是使用类和
\uu getattr\uuu
类来实现这类功能。然而,我也尝试在
sys.modules
中搜索,并得出以下结论:

# mymod.py
def greet(greeting="Hello World"):
   print greeting

class autoload(object):
    def __init__(self, __name__):
        super(autoload, self).__init__()
        self.wrapped_name = __name__
        self.wrapped = sys.modules[__name__]
    def __getattr__(self, name):
        try:
            return getattr(self.wrapped, name)
        except AttributeError:
            def f():
                greet(name+" "+self.wrapped_name)
            return f

if __name__ != "__main__":
    import sys
    sys.modules[__name__] = autoload(__name__)
从用户的角度来看,这确实是我希望的工作方式:

~> python
Python 2.5.1 (r251:54863, Jan 10 2008, 18:01:57)
[GCC 4.2.1 (SUSE Linux)] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> import mymod
>>> mymod.hello()
hello
>>> from mymod import Hello_World
>>> Hello_World()
Hello_World
但这让我震惊——有没有一种人们倾向于用python自动加载的标准方法

其次,对于有经验的python开发人员来说,一个问题是“这对您来说是好的还是坏的做法”?我是一名经验丰富的python开发人员,我觉得它非常有用,但我觉得它有点边缘化,并且对这是否可以被视为好的实践、坏的实践或类似的实践感兴趣

谢谢

“惰性导入”可以构建在中指定的“导入挂钩”之上,现在已经完全实现。PEP 369曾经涵盖“惰性导入”和导入后挂钩,但后来被简化,现在只涵盖导入后挂钩;尽管如此,您可能会对以下内容感兴趣


可以在中找到通过
meta\u路径
钩子的“惰性导入”的良好实现。

不,我认为这没有用

为什么要为您试图从模块中获取的每个属性动态创建一个函数?我觉得很困惑。似乎新函数是由magic创建的,因此必须深入研究实现以了解正在发生的事情。所有这些都没有语法上的好处

即使你有很好的理由这么做,为什么要用模块呢?为什么要在
sys.modules
中注册类实例?我认为,在python中,让事物呈现出它们不是的样子是不受欢迎的


除非您有意混淆代码,否则我不明白为什么要这么做。

要回答使用类模拟模块的问题:

是的,功能不是偶然的。它在2.x系列的早期就已经存在,在3.x系列中仍然有效

要回答延迟加载问题,请执行以下操作:


有几种方法可以做到这一点,每一种都有点神秘。使用模块模拟器是一种很好的方法。

这在某些情况下当然很有用,例如,当您希望最小化导入时间时。但这总是有界限的,而且会使事情变得更复杂(特别是调试)。进口挂钩很难适用于所有情况。我会尽可能避免使用fir‘核心’库,这些库的主要用途是在其主要用途之外使用。+1供David评论。延迟导入为任何模块的状态增加了额外的复杂性。的确,编写导入语句可能会节省一些时间,但在调试过程中会浪费这些时间。顺便说一句,许多现代IDE都具有管理导入的能力。查看Eclipse上的pydev。对于RESTAPI包装器之类的东西,例如函数名成为URI,它非常有用。为每个函数命名是愚蠢的。让每个函数名都是字符串会导致用户的代码更难阅读,而不是更容易阅读。@ErikAronesty就在这里,为方便起见,它可以很容易地包装上游API,并将验证等留给另一方。此外,跟踪API更改还需要较少的手动工作和维护。我所考虑的原始上下文是基于对网络进行搜索,并基于网络上设备提供的API提供API。因此@ErikAronesty的观点特别贴切。(能够手动更新这将是不切实际的)顺便说一句,这允许这样的事情:从networkdevices.local导入robot robot.forward()打印(“Speed=,robot.Speed”),这非常好用。如果可以的话,我会删除这个,因为对问题文本、代码和标记的更改不再反映我原来的问题。下面的答案也不是特别有用。我真的希望人们在修改别人的问题文本之前能真正提问。例如,原始代码使用“\uuuu name\uuuuu”而不是“mod\u name”的原因是为了显示与sys.modules[\uuuu name\uuuu]的直接相似性,依此类推。这已被编辑破坏。