首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >递归导入:“导入”与“从.导入.”

递归导入:“导入”与“从.导入.”
EN

Stack Overflow用户
提问于 2016-03-25 11:39:30
回答 2查看 6.1K关注 0票数 7

我有两个文件需要相互使用不同的功能。

file1.py

代码语言:javascript
复制
import file2   # from file2 import y2

def x1():
    print "x1"

def x2():
    print "x2"
    file2.y2()

file2.py

代码语言:javascript
复制
import file1   # from file1 import x1

def y1():
    file1.x1()
    print "y"

def y2():
    print "y2"

if __name__ == "__main__":
    y1()

我想知道为什么使用import file1是有效的,但是从file1 (from file1 import x1)导入特定的函数不是吗?

代码语言:javascript
复制
Traceback (most recent call last):
  File "file2.py", line 1, in <module>
    from file1 import x1
  File "file1.py", line 1, in <module>
    import file2
  File "file2.py", line 1, in <module>
    from file1 import x1
ImportError: cannot import name x1

我读过this关于进口的文章:

import X

导入模块X,并在当前命名空间中创建对该模块的引用。然后,您需要定义已完成的模块路径,以便从模块内部访问特定的属性或方法(例如:X.nameX.attribute)

from X import *

导入模块X,并创建对该模块在当前命名空间中定义的所有公共对象的引用(即,所有没有以_开头的名称)或任何您提到的名称的引用。 换句话说,在运行此语句之后,您可以简单地使用一个简单的(非限定的)名称来引用模块X中定义的内容。但是X本身没有定义,所以X.name不能工作。如果已经定义了name,那么它将被新版本所取代。如果将X中的名称更改为指向其他对象,您的模块将不会注意到。 这使得来自模块的所有名称都可以在本地命名空间中使用。

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2016-04-11 19:27:36

循环导入通常表示设计问题,但为了解决这些问题,您可以在底部编写import语句,如下所示:

代码语言:javascript
复制
def x1():
    print "x1"

def x2():
    print "x2"
    file2.y2()

from file2 import y2

记住这是个解决办法。from x import y在循环导入的情况下不能工作的原因是,当您到达第一个from ... import ...时,您将被传递给第二个模块,当第二个模块调用第一个模块时,解释器会意识到它是一个永无止境的循环,并继续使用一个部分导入的模块,甚至在定义函数(即y2还不存在)之前就会发生这种情况。

票数 4
EN

Stack Overflow用户

发布于 2021-01-22 16:24:25

另一种解决方案是只在需要时导入模块。例如,在您的情况下,可以通过以下方法解决这个问题:

file1.py

代码语言:javascript
复制
# insted of importing file2 here

def x1():
    print "x1"

def x2():
    print "x2"
    import file2    # import here when you need it
    file2.y2()

file2.py

此文件内容应与问题中提到的相同。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/36219225

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档