Pregunta ¿Para qué sirve __init__.py?


Que es __init__.py para en un directorio de origen de Python?


1411
2018-01-15 20:09


origen


Respuestas:


Es parte de un paquete. Aquí está la documentación.

los __init__.py se requieren archivos para hacer que Python considere que los directorios contienen paquetes; esto se hace para evitar directorios con un nombre común, como string, desde ocultar involuntariamente módulos válidos que ocurren más tarde (más profundamente) en la ruta de búsqueda del módulo. En el caso más simple, __init__.py puede ser solo un archivo vacío, pero también puede ejecutar el código de inicialización para el paquete o configurar el __all__ variable, que se describe más adelante.


975
2018-01-15 20:13



Archivos nombrados __init__.py se utilizan para marcar directorios en el disco como directorios de paquetes de Python. Si tienes los archivos

mydir/spam/__init__.py
mydir/spam/module.py

y mydir está en su camino, puede importar el código en module.py como

import spam.module

o

from spam import module

Si eliminas el __init__.py archivo, Python ya no buscará submódulos dentro de ese directorio, por lo que los intentos de importar el módulo fallarán.

los __init__.py el archivo generalmente está vacío, pero se puede usar para exportar partes seleccionadas del paquete con un nombre más conveniente, funciones de conveniencia, etc. Dado el ejemplo anterior, se puede acceder al contenido del módulo init como

import spam

Residencia en esta


597
2017-11-07 03:31



Además de etiquetar un directorio como un paquete de Python y definir __all__, __init__.py le permite definir cualquier variable en el nivel del paquete. Hacerlo a menudo es conveniente si un paquete define algo que se importará con frecuencia, de manera similar a API. Este patrón promueve la adherencia a la filosofía de Pythonic "el plano es mejor que el anidado".

Un ejemplo

Aquí hay un ejemplo de uno de mis proyectos, en el cual frecuentemente importo un sessionmaker llamado Session para interactuar con mi base de datos Escribí un paquete de "base de datos" con algunos módulos:

database/
    __init__.py
    schema.py
    insertions.py
    queries.py

Mi __init__.py contiene el siguiente código:

import os

from sqlalchemy.orm import sessionmaker
from sqlalchemy import create_engine

engine = create_engine(os.environ['DATABASE_URL'])
Session = sessionmaker(bind=engine)

Como yo defino Session aquí, puedo comenzar una nueva sesión usando la siguiente sintaxis. Este código sería el mismo ejecutado desde dentro o fuera del directorio del paquete "base de datos".

from database import Session
session = Session()

Por supuesto, esta es una pequeña conveniencia, la alternativa sería definir Session en un nuevo archivo como "create_session.py" en mi paquete de base de datos, e inicie nuevas sesiones usando:

from database.create_session import Session
session = Session()

Otras lecturas

Existe un hilo reddit bastante interesante que cubre los usos apropiados de __init__.py aquí:

http://www.reddit.com/r/Python/comments/1bbbwk/whats_your_opinion_on_what_to_include_in_init_py/

La opinión de la mayoría parece ser que __init__.py los archivos deben ser muy delgados para evitar violar la filosofía "explícita es mejor que implícita".


366
2017-09-24 10:38



Hay 2 razones principales para __init__.py

  1. Por conveniencia: los otros usuarios no necesitarán conocer la ubicación exacta de sus funciones en la jerarquía de su paquete.

    your_package/
      __init__.py
      file1.py/
      file2.py/
        ...
      fileN.py
    
    # in __init__.py
    from file1 import *
    from file2 import *
    ...
    from fileN import *
    
    # in file1.py
    def add():
        pass
    

    luego otros pueden llamar a add () por

    from your_package import add
    

    sin saber file1, como

    from your_package.file1 import add
    
  2. Si quieres que algo se inicialice; por ejemplo, el registro (que debe colocarse en el nivel superior):

    import logging.config
    logging.config.dictConfig(Your_logging_config)
    

103
2018-04-08 08:29



los __init__.py archivo hace que Python trate los directorios que lo contienen como módulos.

Además, este es el primer archivo que se carga en un módulo, por lo que puede usarlo para ejecutar el código que desea ejecutar cada vez que se carga un módulo, o especificar los submódulos que se exportarán.


87
2018-01-15 20:22



Desde Python 3.3, __init__.py ya no se requiere para definir directorios como paquetes importables de Python.

Comprobar PEP 420: paquetes de espacios de nombres implícitos:

Soporte nativo para directorios de paquetes que no requieren __init__.py los archivos de marcadores y pueden abarcar automáticamente múltiples segmentos de ruta (inspirados en diversos enfoques de terceros sobre paquetes de espacios de nombres, como se describe en PEP 420)

Aquí está la prueba:

$ mkdir -p /tmp/test_init
$ touch /tmp/test_init/module.py /tmp/test_init/__init__.py
$ tree -at /tmp/test_init
/tmp/test_init
├── module.py
└── __init__.py
$ python3

>>> import sys
>>> sys.path.insert(0, '/tmp')
>>> from test_init import module
>>> import test_init.module

$ rm -f /tmp/test_init/__init__.py
$ tree -at /tmp/test_init
/tmp/test_init
└── module.py
$ python3

>>> import sys
>>> sys.path.insert(0, '/tmp')
>>> from test_init import module
>>> import test_init.module

referencias:
https://docs.python.org/3/whatsnew/3.3.html#pep-420-names-namespace-packages
https://www.python.org/dev/peps/pep-0420/
¿No se requiere __init__.py para paquetes en Python 3? 


45
2017-10-12 06:36



En Python, la definición de paquete es muy simple. Al igual que Java, la estructura jerárquica y la estructura del directorio son las mismas. Pero debes tener __init__.py en un paquete Explicaré el __init__.py archivo con el siguiente ejemplo:

package_x/
|--  __init__.py
|--    subPackage_a/
|------  __init__.py
|------  module_m1.py
|--    subPackage_b/
|------  __init__.py
|------  module_n1.py
|------  module_n2.py
|------  module_n3.py

__init__.py puede estar vacío, mientras exista. Indica que el directorio debe considerarse como un paquete. Por supuesto, __init__.py también puede establecer el contenido apropiado.

Si agregamos una función en module_n1:

def function_X():
    print "function_X in module_n1"
    return

Despues de correr:

>>>from package_x.subPackage_b.module_n1 import function_X
>>>function_X()

function_X in module_n1 

Luego seguimos el paquete de jerarquía y llamamos a module_n1 la función. Nosotros podemos usar __init__.py en subPackage_b así:

__all__ = ['module_n2', 'module_n3']

Despues de correr:

>>>from package_x.subPackage_b import * 
>>>module_n1.function_X()

Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ImportError: No module named module_n1

Por lo tanto, al usar * la importación, el paquete del módulo está sujeto a __init__.py contenido.


44
2018-01-09 11:45



__init__.py tratará el directorio en el que se encuentra como un módulo cargable.

Para las personas que prefieren leer código, puse Alquimista de dos bits comentar aquí.

$ find /tmp/mydir/
/tmp/mydir/
/tmp/mydir//spam
/tmp/mydir//spam/__init__.py
/tmp/mydir//spam/module.py
$ cd ~
$ python
>>> import sys
>>> sys.path.insert(0, '/tmp/mydir')
>>> from spam import module
>>> module.myfun(3)
9
>>> exit()
$ 
$ rm /tmp/mydir/spam/__init__.py*
$ 
$ python
>>> import sys
>>> sys.path.insert(0, '/tmp/mydir')
>>> from spam import module
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ImportError: No module named spam
>>> 

35
2018-01-03 17:41



¿Para qué se utiliza __init__.py?

El uso principal de __init__.py es inicializar los paquetes de Python. La forma más fácil de demostrar esto es echar un vistazo a la estructura de un módulo Python estándar.

package/
    __init__.py
    file.py
    file2.py
    file3.py
    subpackage/
        __init__.py
        submodule1.py
        submodule2.py

Como puede ver en la estructura anterior a la inclusión del __init__.py archivo en un directorio indica al intérprete de Python que el directorio debe tratarse como un paquete de Python

Lo que entra __init__.py?

__init__.py puede ser un archivo vacío, pero a menudo se usa para realizar la configuración necesaria para el paquete (importar cosas, cargar cosas en la ruta, etc.).

Una cosa común para hacer en su __init__.py es importar Clases seleccionadas, funciones, etc. al nivel del paquete para que puedan ser importadas convenientemente desde el paquete.

En el ejemplo anterior, podemos decir que file.py tiene el archivo de clase. Entonces sin nada en nuestro __init__.py importarías con esta sintaxis:

from package.file import File

Sin embargo, puede importar el archivo a su __init__.py para que esté disponible a nivel de paquete:

# in your __init__.py
from file import File

# now import File from package
from package import File

Otra cosa que hacer es a nivel del paquete hacer subpaquetes / módulos disponibles con el __all__ variable. Cuando el interperador ve una __all__ variable definida en una __init__.py importa los módulos enumerados en __all__ variable cuando lo haces:

from package import *

__all__es una lista que contiene los nombres de los módulos que desea importar con la importación *, por lo tanto, si volvemos a ver nuestro ejemplo anterior, si queremos importar los submódulos en el subpaquete, __all__ variable en subpackage/__init__.py sería:

__all__ = ['submodule1', 'submodule2']

Con el __all__ variable poblada así, cuando actúas

from subpackage import *

importaría el submódulo1 y el submódulo2.

Como puedes ver __init__.py puede ser muy útil además de su función principal de indicar que un directorio es un módulo.

Referencia


26
2017-12-17 06:09