简体   繁体   English

如何从子函数将模块导入main()?

[英]How can I import a module into main() from a sub function?

In a Python script, I would like to control the importing of a module into the main() from a sub function. 在Python脚本中,我想控制模块从子函数到main()的导入。 Is this possible? 这可能吗? How? 怎么样?

Why: I have a sub function that handles command line arguments (using argparse) and would like to import a module based on user input. 原因:我有一个子函数来处理命令行参数(使用argparse),并希望基于用户输入导入模块。 Specifically, I would like to let the user specify the backend for matplotlib, which has to be set before importing matplotlib.pylab. 具体来说,我想让用户指定matplotlib的后端,必须在导入matplotlib.pylab之前对其进行设置。 However, I think the question has more general use. 但是,我认为这个问题具有更广泛的用途。

Here is a code snippet: 这是一个代码片段:

def main():

    args = handleCommandLine();

    fig, ax = plt.subplots(1)   # ERROR: plt not defined

    # Snip ...


def handleCommandLine():
    p = argparse.ArgumentParser()
    p.add_argument('--backend', '-b', default=None, help='Specify plotting backend')
    args = p.parse_args()

    if args.backend != None:
        matplotlib.use(args.backend)  #Must occur before importing pyplot

    import matplotlib.pyplot as plt   #Must occur after setting backend, if desired
    return args

If you'd like it to behave as though you executed import matplotlib.pyplot as plt at the top of the module, even though you didn't, use a global: 如果您希望它的行为就像您在模块顶部的import matplotlib.pyplot as plt一样执行import matplotlib.pyplot as plt ,即使您没有这样做,也可以使用全局变量:

def handleCommandLine():
    p = argparse.ArgumentParser()
    p.add_argument('--backend', '-b', default=None, help='Specify plotting backend')
    args = p.parse_args()

    if args.backend != None:
        matplotlib.use(args.backend)  #Must occur before importing pyplot

    global plt  #Style choice: Can also be placed at the top of the function
    import matplotlib.pyplot as plt  #Must occur after setting backend
    return args

Otherwise you can pass the included library reference through a function return, in the same way you handle any other variable: 否则,可以像处理任何其他变量一样,通过函数返回传递包含的库引用:

def main():
    plt, args = handleCommandLine()   # CHANGED HERE
    fig, ax = plt.subplots(1)
    # ...    

def handleCommandLine():
    p = argparse.ArgumentParser()
    p.add_argument('--backend', '-b', default=None, help='Specify plotting backend')
    args = p.parse_args()

    if args.backend != None:
        matplotlib.use(args.backend)  #Must occur before importing pyplot

    import matplotlib.pyplot as plt   #Must occur after setting backend, if desired
    return plt, args   # CHANGED HERE

An import statement is much like an assignment -- it assigns to a local name, unless you explicitly declare as global . import语句非常类似于赋值-除非您显式声明为global ,否则它将分配给本地名称。 The following imports plt into the global namespace: 以下进口plt到全局命名空间:

def handleCommandLine():
    global plt
    ...
    import matplotlib.pyplot as plt

You can't. 你不能

I'd solve this by either returning plt from handleCommandLine or moving the import to main . 我可以通过从handleCommandLine返回plt或将导入移动到main来解决此问题。

global plt放在handleCommandLine()的开头。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM