“导入*”导入到底是什么?

“导入*”导入到底是什么?

问题描述:

在Python中,import *究竟导入了什么?它是否在包含文件夹中找到__init__.py“导入*”导入到底是什么?

例如,是否有必要声明from project.model import __init__或者from project.model import *是否足够?

+0

'from yadda.yadda import *'在黑客攻击Python命令行中的内容时非常有用,例如,当你使用Python作为计算器时,你只需输入'from math import *'。在一个模块中,它要求麻烦。另外,如果您导入单个文件模块(而不是目录),'from ... import *'将不会导入名称以'_'开头的符号。 – 2010-03-02 03:51:46

相对于其他形式进口的from xyz import *的“好处”是,进口一切(好,几乎... [见(a)所示]的所有内容)从当前模块下指定的模块。这允许使用来自导入模块的各种对象(变量,类别,方法...),而无需在模块的名称前添加。例如

>>> from math import * 
>>>pi 
3.141592653589793 
>>>sin(pi/2) 
>>>1.0 

这种做法(输入*到当前的命名空间),然而,鼓励,因为它 它

  • 提供了机会,命名空间冲突(比方说,如果你有一个变量名PI在导入之前)
  • 可能效率低下,如果导入的对象数量很大。
  • 没有明确文件变量/方法/类的起源(它是好的,有计划的对未来的此次访问“自文档”到代码中)

通常我们因此限制了这种进口*实践即席测试之类的,而是:

明确导入几个对象只

>>>from math import pi 
>>>pi 
>>>3.141592653589793 
>>> sin(pi/2) 
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
NameError: name 'sin' is not defined 

导入模根据其自己的名称空间 ULE(或别名物,特别是如果这是一个长的名称,并且该程序引用其对象多次)

>>>import math 
    >>>math.pi 
    >>>3.141592653589793 
    etc.. 


    >>>import math as m #bad example math being so short and standard... 
    >>>m.pi 
    >>>3.141592653589793 
    etc.. 

参见Python documentation on this topic

的(a)具体地,与from xyz import *导入的内容
如果xyz模块定义了一个__all__变量,它将导入在此序列中定义的所有名称,否则它将导入所有名称,除了以下划线开头的所有名称。

+7

'从X导入*'的优点是它可以让你很懒惰。它的问题是,它会咬你懒惰的屁股:) – voyager 2010-03-02 04:14:19

+1

一些模块(如['pygame'](http://www.pygame.org/docs/ref/locals.html),但许多其他)有一个特殊的子模块,目的是作为'*'导入。这些特殊模块通常具有常用的常量或功能。 – 2011-01-25 01:55:43

+0

因此,基本上我可以导入一切,而不会得到名称空间冲突,如果我使用'import math'而不是'从数学导入*'? – 2014-11-16 13:59:17

是的,它的确如此。它会导入所有内容(这不是私有变量,即:名称以___开头的变量),您应该尽量不要根据“Properly importing modules in Python”使用它以避免污染本地名称空间。

这是不够的,但通常您应该做import project.model,已经进口__init__.py,每个“Understanding python imports”,但可以得到,如果你使用它太多,或import project.model as pmimport project.model as model节省几个按键后来当太罗嗦你用吧。

按照亚历克斯在咨询“What exactly does "import *" import?

+6

良好的推荐,但不准确的信息:'从foo导入*'不**“导入所有内容” - 它导入模块的__all__属性中列出的名称,或者缺少该属性_non-private_ names(不包括以'_'开头的名称)。 – 2010-03-02 03:50:48

+0

@亚历克斯,好点。你想扩大它,还是你更喜欢我这么做? – voyager 2010-03-02 04:13:04

+0

我已经扩充了它 - 请参阅我对这个问题的回答。 – 2010-03-02 04:16:07

如果project.model是一个包,通过import project.model提到的模块是从.../project/model/__init__.pyfrom project.model import *__init__.py的命名空间中的所有内容都转储为您的。它不会自动对模型中的其他模块执行任何操作。首选的样式是__init__.py不包含任何内容。

永远不会永远使用import *。它使你的代码不可读,不可维护。

如果有问题的模块(project.model)已经定义了名为__all__的响应列表,那么该列表中的每个命名变量都会被导入。如果没有这样的变量,它会导入一切。

它将模块(或包)在其__all__属性中列出的任何名称(到当前名称空间中)导入 - 缺少这样的属性,所有名称不以_开头。

它主要用作只在交互式解释器会话中使用一个方便快捷:其他答案建议,在程序中使用它。

我的建议,每Google's Python style guide,是永远只导入模块,从模块中类或函数(或其他名称)。严格遵循这一点可以提高清晰度和精确度,并避免在从模块中导入“材料”时可能出现的细微陷阱。

导入程序包(或其中的任何内容)会固有加载并执行程序包的__init__.py - 该文件定义程序包的主体。但是,它不会在当前名称空间中绑定名称__init__(因此从这个意义上说,它不会导入该名称)。

+0

所以基本上我可以导入一切都没有得到名称空间相撞,如果我使用'导入数学'而不是'从数学导入*'? – 2014-11-16 13:59:46