惰性模块变量——可以做到吗? [英] Lazy module variables--can it be done?
问题描述
我正在尝试找到一种延迟加载模块级变量的方法.
I'm trying to find a way to lazily load a module-level variable.
具体来说,我编写了一个小型 Python 库来与 iTunes 对话,并且我想要一个 DOWNLOAD_FOLDER_PATH
模块变量.不幸的是,iTunes 不会告诉你它的下载文件夹在哪里,所以我写了一个函数来获取一些播客曲目的文件路径并爬回目录树,直到找到下载"目录.
Specifically, I've written a tiny Python library to talk to iTunes, and I want to have a DOWNLOAD_FOLDER_PATH
module variable. Unfortunately, iTunes won't tell you where its download folder is, so I've written a function that grabs the filepath of a few podcast tracks and climbs back up the directory tree until it finds the "Downloads" directory.
这需要一两秒钟,所以我希望延迟评估它,而不是在模块导入时.
This takes a second or two, so I'd like to have it evaluated lazily, rather than at module import time.
有没有办法在第一次访问模块变量时懒惰地分配它,或者我必须依赖一个函数?
Is there any way to lazily assign a module variable when it's first accessed or will I have to rely on a function?
推荐答案
你不能用模块来做到这一点,但你可以把一个类伪装"成一个模块,例如,在 itun.py 中
, 代码...:
You can't do it with modules, but you can disguise a class "as if" it was a module, e.g., in itun.py
, code...:
import sys
class _Sneaky(object):
def __init__(self):
self.download = None
@property
def DOWNLOAD_PATH(self):
if not self.download:
self.download = heavyComputations()
return self.download
def __getattr__(self, name):
return globals()[name]
# other parts of itun that you WANT to code in
# module-ish ways
sys.modules[__name__] = _Sneaky()
现在任何人都可以import itun
...并获得你的itun._Sneaky()
实例.__getattr__
允许您访问 itun.py
中的任何其他内容,这些内容可能比在 内部更方便您将其编码为顶级模块对象_偷偷摸摸的
!_)
Now anybody can import itun
... and get in fact your itun._Sneaky()
instance. The __getattr__
is there to let you access anything else in itun.py
that may be more convenient for you to code as a top-level module object, than inside _Sneaky
!_)
这篇关于惰性模块变量——可以做到吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!