导入以下划线

时间:2015-07-20 14:59:52

标签: python

我正在编写一个简单的Python库,其中有几个" private"以下划线开头的函数:

def _a():
    pass

def _b():
    pass

def public_interface_call():
    _a()
    _b()

通过这种方式,我的图书馆用户可以简单地执行from MyLib.Module import *,并且他们的名称空间不会因实施细节而变得混乱。

然而,我也在编写单元测试,我喜欢单独测试这些功能,简单地从我的模块中导入真正的所有符号将非常方便。目前我正在做from Mylib.Module import _a _b public_interface_call,但我想知道是否有更好/更快/更清洁的方式来实现我想要的目标?

4 个答案:

答案 0 :(得分:7)

当我写这个问题时,我不确定这是停电还是什么,但今天我意识到(受Underyx's comment的启发)我可以这样做:

import MyLib.Module

MyLib.Module._a()
MyLib.Module._b()

甚至可以稍微缩短一点(因为我是一个懒惰的混蛋):

import MyLib.Module as mm

mm._a()
mm._b()

答案 1 :(得分:1)

根据docs

  

甚至还有一个变体可以导入模块定义的所有名称:
  from fibo import *
  ...
  这将导入除以下划线(_)开头的所有名称。

不知道为什么会这样。

答案 2 :(得分:1)

已经为您的问题提供了最佳,最常见的解决方案:

import MyLib.Module as mm

如果仍然想使用变体from MyLib.Module import *,则可以覆盖其默认行为:在模块的源文件MyLib / Module.py中添加列表__all__并声明哪个对象应该被导出。

请注意,您需要对要显示的每个对象执行此操作。这不会影响上述其他导入机制的行为。

示例:

# MyLib/Module.py
__all__ = ["_a", "_b"]

def _a(): pass 
def _b(): pass
def  c(): pass

# ...

# Import
from MyLib.Module import *
# => this imports _a() and _b(), but not c()

要指定软件包索引__all__,可以控制在导入软件包时应加载哪些子模块。有关更多信息,请参见here,有关相关问题,请参见SO thread

答案 3 :(得分:0)

如果您没有编写一些严肃的程序,可以尝试一下

  this.state = { image: '' };

componentDidMount() {
const employees = this.props.employees;
let employee = {};
let employeeID = this.props.match.params.id;
employee = employees[employeeID];
setTimeout(() => {
  this.setState({
    image: employee.profilePicture
  });
}, 500);