2016-06-28 23 views
1

Ich habe die letzte Stunde damit verbracht, Google und SO auf dieser Seite zu durchlaufen. Tut mir leid, dass ich noch einen weiteren Eintrag hinzugefügt habe, aber keine der Antworten funktioniert für mich.Importieren der Python-Klasse aus dem Geschwisterverzeichnis

in /VM/repo/project My Directory-Struktur ist:

__init__.py 

scripts/ 
     getSomething.py 
     __init__.py 

classes/ 
     project.py 
     db.py 
     __init__.py 

====================

getSomething.py

from ..classes import project 
from ..classes import db 

====================

project.py

class PROJECT: 
def __init__(self): 
    stuff 

====================

db.py

class DB: 
def __init__(self): 
    stuff 

=========== =========

Wenn ich versuche,

python getSomething.py

ich erhalte den Fehler

0 zu laufen

Was fehlt mir hier?

Antwort

4

Wie in dem Fehler angegeben, führen Sie getSomething als Hauptmodul. Sie können jedoch keine relativen Paketimporte durchführen, wenn Sie nicht in einem Paket sind. Das Hauptmodul ist nie in einem Paket. Also, wenn Sie getSomething als Teil eines Pakets importieren waren ...:

# /VM/repo/main.py 
from project.scripts import getSomething 

Dann würden Sie nicht die Importfehler haben.


Vielleicht ist es hilfreich, eine kurze Diskussion über Python-Module und -Pakete zu haben. Im Allgemeinen ist eine Datei, die Python-Quellcode enthält und die Erweiterung .py hat, ein Modul. Normalerweise ist der Name dieses Moduls der Name der Datei (ohne Erweiterung), aber wenn Sie ihn direkt ausführen, lautet der Name des Moduls '__main__'. Bisher ist dies alles bekannt und dokumentiert. Um ein Modul zu importieren, tun Sie einfach import module oder import package.module und so weiter. Diese letzte Importanweisung bezieht sich auf etwas anderes (ein "Paket"), über das wir jetzt sprechen werden ...

Pakete sind Verzeichnisse, die Sie importieren können. Viele Verzeichnisse können nicht importiert werden (z. B. haben sie keine Python-Quelldateien - Module - in ihnen). Um diese Mehrdeutigkeit aufzulösen, gibt es auch die Anforderung, dass das Verzeichnis eine __init__.py Datei hat. Wenn Sie ein Verzeichnis in Ihr Dateisystem importieren, importiert Python das Modul __init__.py und erstellt das zugehörige Paket aus den Dingen in __init__.py (falls vorhanden).

all das Zusammenstellen zeigt, warum eine Datei in einem Verzeichnis ausgeführt werden, die eine __init__.py hat, ist nicht genug für Python das Modul zu prüfen, ist Teil eines Pakets zu sein. Zunächst lautet der Name des Moduls __main__, nicht package.filename_sans_extension.Zweitens hängt die Erstellung eines Pakets nicht nur von der Dateisystemstruktur ab, sondern auch davon, ob das Verzeichnis (und damit __init__.py tatsächlich importiert wurde).

Sie fragen sich vielleicht: "Warum haben sie es so entworfen?" In der Tat habe ich mich gelegentlich dieselbe Frage gestellt. Ich denke, dass der Grund dafür ist, dass die Sprachdesigner bestimmte Garantien für ein Paket wünschen. Ein Paket sollte eine Einheit von Dingen sein, die so konzipiert sind, dass sie für einen bestimmten Zweck zusammenarbeiten. Es sollte kein Silo von Skripten sein, die aufgrund einiger zufälliger __init__.py Dateien die Fähigkeit erhalten, durch das Dateisystem zu laufen, um die anderen Module zu finden, die sie benötigen. Wenn etwas als Hauptmodul ausgeführt wird, sollte es wahrscheinlich nicht Teil des Pakets sein. Es sollte vielmehr ein separates Modul sein, das das Paket importiert und darauf vertraut.

+0

Okay, also ein paar Dinge: Ich hatte den Eindruck, dass das Hinzufügen von '__init __. Py' zu jedem Verzeichnis im Wesentlichen diese Verzeichnisse als ein Paket definiert? Ich könnte hier ein grundsätzliches Missverständnis von Paketen haben. Warum ist das Hauptmodul nie in einem Paket? Zweitens: Mein Ziel ist es, die Skripte auf einem Cron zu laufen. Gibt es keine Möglichkeit, die Klassen direkt in die Skripte zu importieren? Eine weitere Datei 'main.py' zu erstellen, scheint unnötig kompliziert zu sein. – ShaneOH

+1

@ShaneOH - Ich habe versucht (so gut ich kann), meine Antwort zu bearbeiten, um hoffentlich alle Unklarheiten zu beseitigen ... Ich hoffe, es hilft. – mgilson

+0

Danke, die ursprüngliche Antwort und Bearbeitung sind beide sehr hilfreich. Also habe ich eine letzte Frage: Was ist, wenn ich diese Verzeichnisstruktur behalten und die Skripte direkt als Hauptmodule ausführen möchte? Okay, sie müssen nicht Teil des Pakets sein. Wie importiere ich die Module/classes in ein Hauptmodul in einem Geschwisterordner? Und entferne ich dann "__init __. Py" aus/scripts und aus/project? – ShaneOH