it-swarm.com.de

Relative Importe - ModuleNotFoundError: Kein Modul mit dem Namen x

Dies ist das erste Mal, dass ich mich wirklich hinsetze und python 3 probiere und scheine kläglich zu versagen. Ich habe die folgenden zwei Dateien:

  1. test.py
  2. config.py

in config.py sind einige Funktionen sowie einige Variablen definiert. Ich habe es auf Folgendes reduziert:

enter image description here

Ich erhalte jedoch den folgenden Fehler:

ModuleNotFoundError: No module named 'config'

Mir ist bewusst, dass die py3-Konvention absolute Importe verwendet:

from . import config

Dies führt jedoch zu folgendem Fehler:

ImportError: cannot import name 'config'

Ich bin also ratlos, was ich hier tun soll ... Jede Hilfe wird sehr geschätzt. :)

90
blitzmann

Wie in den Kommentaren zum ursprünglichen Beitrag angegeben, schien dies ein Problem mit dem python -Interpreter zu sein, den ich aus irgendeinem Grund verwendete, und nicht mit den python -Skripten. Ich habe vom WinPython-Bundle auf das offizielle python 3.6 von python.org umgestellt und es hat einwandfrei funktioniert. danke für die hilfe an alle :)

1
blitzmann

TL; DR: Sie können keine relativen Importe aus der Datei durchführen, die Sie ausführen, da das __main__ -Modul kein Teil eines Pakets ist.

Absolute Importe - etwas importieren, das in sys.path verfügbar ist

Relative Importe - importiere etwas relativ zum aktuellen Modul, muss Teil eines Pakets sein

Wenn Sie beide Varianten auf die gleiche Weise ausführen, sollte eine davon funktionieren. Hier ist ein Beispiel, das Ihnen helfen soll zu verstehen, was los ist. Fügen wir eine weitere main.py -Datei mit der folgenden allgemeinen Verzeichnisstruktur hinzu:

.
./main.py
./ryan/__init__.py
./ryan/config.py
./ryan/test.py

Und aktualisieren wir test.py, um zu sehen, was los ist:

# config.py
debug = True


# test.py
print(__name__)

try:
    # Trying to find module in the parent package
    from . import config
    print(config.debug)
    del config
except ImportError:
    print('Relative import failed')

try:
    # Trying to find module on sys.path
    import config
    print(config.debug)
except ModuleNotFoundError:
    print('Absolute import failed')


# main.py
import ryan.test

Lassen Sie uns zuerst test.py ausführen:

$ python ryan/test.py
__main__
Relative import failed
True

Hier ist "test" das Modul __main__ und weiß nichts über die Zugehörigkeit zu einem Paket. Allerdings sollte import config funktionieren, da der Ordner ryan zu sys.path hinzugefügt wird.

Führen wir stattdessen main.py aus:

$ python main.py
ryan.test
True
Absolute import failed

Und hier Test ist innerhalb des "Ryan" -Pakets und kann relative Importe durchführen. import config schlägt fehl, da implizite relative Importe in Python 3 nicht zulässig sind.

Hoffe das hat geholfen.

P.S .: Wenn Sie sich an Python 3 halten, brauchen Sie die __init__.py -Dateien nicht mehr.

110
Igonato

Ich habe es herausgefunden. Sehr frustrierend, vor allem von Python2.

Sie müssen dem Modul einen . hinzufügen, unabhängig davon, ob es relativ oder absolut ist.

Ich habe das Verzeichnissetup wie folgt erstellt.

/main.py
--/lib
  --/__init__.py
  --/mody.py
  --/modx.py

modx.py

def does_something():
    return "I gave you this string."

mody.py

from modx import does_something

def loaded():
    string = does_something()
    print(string)

main.py

from lib import mody

mody.loaded()

wenn ich main ausführe, passiert folgendes

$ python main.py
Traceback (most recent call last):
  File "main.py", line 2, in <module>
    from lib import mody
  File "/mnt/c/Users/Austin/Dropbox/Source/Python/virtualenviron/mock/package/lib/mody.py", line 1, in <module>
    from modx import does_something
ImportError: No module named 'modx'

Ich habe 2to3 ausgeführt, und die Kernausgabe war dies

RefactoringTool: Refactored lib/mody.py
--- lib/mody.py (original)
+++ lib/mody.py (refactored)
@@ -1,4 +1,4 @@
-from modx import does_something
+from .modx import does_something

 def loaded():
     string = does_something()
RefactoringTool: Files that need to be modified:
RefactoringTool: lib/modx.py
RefactoringTool: lib/mody.py

Ich musste die Importanweisung von mody.py ändern, um das Problem zu beheben

try:
    from modx import does_something
except ImportError:
    from .modx import does_something


def loaded():
    string = does_something()
    print(string)

Dann lief ich wieder main.py und bekam die erwartete Ausgabe

$ python main.py
I gave you this string.

Zuletzt, nur um es aufzuräumen und zwischen 2 und 3 portabel zu machen.

from __future__ import absolute_import
from .modx import does_something
41
user3159377

Das Einstellen von PYTHONPATH kann auch bei diesem Problem helfen.

So kann es unter Windows gemacht werden

set PYTHONPATH=.

21
Santosh Pillai

Versuchte dein Beispiel

from . import config

hat folgenden Systemfehler erhalten:
/usr/bin/python3.4 test.py
Traceback (letzter Anruf zuletzt):
Datei "test.py", Zeile 1, in
von . Konfiguration importieren
SystemError: Übergeordnetes Modul '' nicht geladen, relativer Import nicht möglich


Das wird bei mir funktionieren:

import config
print('debug=%s'%config.debug)

>>>debug=True

Getestet mit Python: 3.4.2 - PyCharm 2016.3.2


Außerdem bietet PyCharm an, diesen Namen zu importieren .
Sie müssen auf config klicken und ein Hilfesymbol wird angezeigt. enter image description here

10
stovfl

Sie können einfach die folgende Datei zu Ihrem Testverzeichnis hinzufügen und python führt sie vor den Tests aus

__init__.py file

import os
import sys
sys.path.insert(0, os.path.abspath(os.path.join(os.path.dirname(__file__), '..')))
6
Vinod Rane

Sie müssen den Pfad des Moduls an PYTHONPATH anhängen:

export PYTHONPATH="${PYTHONPATH}:/path/to/your/module/"
5

Dieses Beispiel funktioniert mit Python 3.6.

Ich empfehle, in PyCharm zu Run -> Edit Configurations zu wechseln, alle Einträge dort zu löschen und erneut zu versuchen, den Code über PyCharm auszuführen.

Wenn dies nicht funktioniert, überprüfen Sie Ihren Projektinterpreter (Einstellungen -> Projektinterpreter) und führen Sie die Konfigurationsstandards aus (Ausführen -> Konfigurationen bearbeiten ...).

3
Carson Crane

Deklarieren Sie die korrekte sys.path Liste, bevor Sie das Modul aufrufen:

import os, sys

#'/home/user/example/parent/child'
current_path = os.path.abspath('.')

#'/home/user/example/parent'
parent_path = os.path.dirname(current_path)

sys.path.append(parent_path)
os.environ.setdefault('Django_SETTINGS_MODULE', 'child.settings')
1
HoangYell