当前位置: 首页 > 知识库问答 >
问题:

Python-为什么我可以导入模块没有__init__。

袁弘方
2023-03-14

我是Python新手,我仍然无法理解为什么我们需要一个\uuu init\uuuu.py文件来导入模块。我已经看过了其他的问题和答案,比如这个。

让我困惑的是,我可以在没有__init__py的情况下导入我的模块,那么为什么我需要它呢?

以我为例,,

index.py
   modules/
      hello/
          hello.py
          HelloWorld.py

index.py,

import os
import sys

root = os.path.dirname(__file__)
sys.path.append(root + "/modules/hello")

# IMPORTS MODULES
from hello import hello
from HelloWorld import HelloWorld

def application(environ, start_response):

    results = []

    results.append(hello())

    helloWorld = HelloWorld()
    results.append(helloWorld.sayHello())

    output = "<br/>".join(results)

    response_body = output

    status = '200 OK'

    response_headers = [('Content-Type', 'text/html'),
                       ('Content-Length', str(len(response_body)))]

    start_response(status, response_headers)

    return [response_body]

模块/hello/hello.py,

def hello():
    return 'Hello World from hello.py!'

模块/Hello/HelloWorld.py,

# define a class
class HelloWorld:
    def __init__(self):
        self.message = 'Hello World from HelloWorld.py!'

    def sayHello(self):
        return self.message

后果

Hello World from hello.py!
Hello World from HelloWorld.py!

只需要这两条线,

root = os.path.dirname(__file__)
sys.path.append(root + "/modules/hello")

没有任何\uuuu init\uuuu py。有人能解释为什么它是这样工作的吗?

如果\uuuu init\uuuu py是正确的方法,我应该在代码中做什么/更改?

共有3个答案

孙明德
2023-03-14

我认为这可能是由于您使用的Python版本。我做了一些实验,发现有以下结构:

jedrzej@jedrzej-UX303LB ~/temp $ tree .
.
├── main.py
└── packages
    ├── file.py
    └── file.pyc

1 directory, 5 files

main.py内容:

import packages.file as p
p.fun()

和file.py的内容:

import sys
def fun():
  print(sys.path)

当我用Python 2.7.12执行main.py时,我得到重要错误,而用Python 3.5.2执行main.py只是工作。

在包目录中添加__init__. py后,代码适用于Python的两个版本。

方楷
2023-03-14

\uuuu init\uuuu.py用于软件包。包包含相关模块的集合。如果您只想使用一个模块,则不需要使用\uuuu init\uuuuuuuuupy;只需将单个.py文件放在系统路径的某个位置,就可以导入它了。

包的目的不仅仅是允许您导入其中的模块。它是将模块组合在一起。这样做的主要好处是,如果一个模块在包中,那么该模块可以使用相对导入从包中导入其他模块。如果你有foo.pybar.py在同一个包中,那么foo就可以从。导入栏执行。这使得包内导入更加紧凑,如果您重组包或更改其名称,则更容易重组。

此外,一个明显的好处是。如果你把它做成一个包,你不必每次想从中导入东西时都去做sys.path之类的事情。

仇正豪
2023-03-14

基于此链接:自Python 3.3以来

允许隐式名称空间包意味着可以完全删除提供\uuuu init\uuuuu.py文件的要求

 类似资料:
  • 问题内容: 我注意到我今天想解释的东西很奇怪。我不是100%不确定如何将其表达为一个问题,所以google是不可能的。由于某些奇怪的原因,日志记录模块无权访问模块logging.handlers。如果您不相信我,请自己尝试: 谁能解释为什么会这样? 问题答案: 在Python中,需要先导入模块,然后才能对其进行访问。仅导入日志记录模块。碰巧这是一个带有子模块的软件包,但是那些子模块仍然不会自动加载

  • 问题内容: 我有一个正在构建的Python程序,可以通过以下两种方式之一运行:第一种是调用,它以友好的方式提示用户输入,然后通过该程序运行用户输入。另一种方法是调用“ ”,它将遍历所有友好的输入集合,并通过该程序一次运行整个文件的输入值。 问题是,当我运行时,它会从中导入一些变量/方法/等,并在运行此代码时: 在程序的第一行,它立即错误,因为它试图运行中的代码。 如何阻止Python运行要导入的“

  • 运行此代码后,我发现导入错误:- 如何使用google.apengine.ext

  • 我正在用Python开发一个包。我使用虚拟环境。我在我的虚拟环境中的. pth路径中设置了模块的根路径,这样我就可以在开发代码和进行测试的同时导入包的模块(问题1:这是一个好方法吗?)。这工作正常(这里有一个例子,这是我想要的行为): 但是,如果我尝试使用PyTest,则会收到一些导入错误消息: 我有点困惑,看起来这表明了一个导入错误,但是Python做得很好,那么为什么PyTest会有问题呢?对

  • 问题内容: 据我了解,python模块永远不会导入两次,即该模块中的代码仅在首次导入时才执行。随后的import语句只需将模块添加到导入范围即可。 我有一个名为“ TiledConvC3D.py”的模块,但似乎已多次导入。我使用pdb在该模块的代码顶部打印堆栈。 这是从第一次执行模块开始的堆栈跟踪的结尾: 它将继续执行多次。但是,第二次调用的完整堆栈跟踪不会显示对的任何调用,因此不应执行这些执行:

  • 问题内容: 在Python中,我有一个 模块 myModule.py,其中定义了一些函数和一个 main() ,它接受了一些命令行参数。 我通常从bash脚本中调用此main()。现在,我想将所有内容放入一个小 包装中 ,因此我想也许可以将我简单的bash脚本转换为Python脚本并将其放入包装中。 因此,实际上如何 从 MyFormerBashScript.py 的main()函数 调用 myM