代码之家  ›  专栏  ›  技术社区  ›  Dims

如何在Python中以编程方式调用函数,同时以编程方式指定模块?

  •  2
  • Dims  · 技术社区  · 7 年前

    import foo
    method_to_call = getattr(foo, 'bar')
    result = method_to_call()
    

    因为模块名是硬编码的,我不能使用它

    module = __import__('foo')
    func = getattr(module, 'bar')
    func()
    

    因为模块是嵌套的。

    我试过这个

    customer = 'jci'
    module = __import__('customer.{customer_name}.gt'.format(customer_name=customer_name)) # AttributeError: module 'customer' has no attribute 'get_gt'
    #module = __import__('customer.{customer_name}'.format(customer_name=customer_name), fromlist=['gt']) # AttributeError: module 'customer.jci' has no attribute 'get_gt'
    #module = __import__('customer.{customer_name}.gt'.format(customer_name=customer_name), fromlist=[]) # AttributeError: module 'customer' has no attribute 'get_gt'
    func = getattr(module, 'get_gt')
    gt = func()    
    

    get_gt() 里面有一个函数吗 gt.py 文件内 customer/jci 目录每个目录都有空的 __init__.py 在…内

    以下硬编码代码有效:

    import customer.jci.gt as g
    gt = g.get_gt()
    

    1 回复  |  直到 7 年前
        1
  •  3
  •   Bakuriu    7 年前

    你想要的是 importlib.import_module


    __import__ 父母亲 包,而不是最后一个孩子。

    证明:

    >>> http = __import__('http.client')
    >>> http.client   # the client submodule was imported
    <module 'http.client' from '/usr/lib/python3.6/http/client.py'>
    >>> # without specifying the .client in the name the submodule is not imported
    >>> __import__('http').client
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
    AttributeError: module 'http' has no attribute 'client'
    

    import_module 而是返回子模块,这是大多数人所期望的:

    >>> importlib.import_module('http.client')
    <module 'http.client' from '/usr/lib/python3.6/http/client.py'>