Datei pfad nicht gefunden

Wenn du dir nicht sicher bist, in welchem der anderen Foren du die Frage stellen sollst, dann bist du hier im Forum für allgemeine Fragen sicher richtig.
Antworten
liddokun88
User
Beiträge: 18
Registriert: Montag 5. März 2012, 16:11

Hallo,

habe ein kleines programm geschrieben das eine .dll aufrufen soll. Öffne ich dieses modul (ABC.py) und klicke auf run, so werden alle funktionen ordnungsgemäß importiert und ich kann diese weiter nutzen.

Nun möchte ich gerne über eine anderes Modul das modul ABC.py aufrufen. Hier verwende ich einfach den befehl:

Code: Alles auswählen

import ABC
Hierbei sagt das programm das es die .dll welche ich über ABC.py aufrufe nicht findet.
Kann mir einer erklären woran das liegt?

Hier noch der Code aus der ABC.py

Code: Alles auswählen

from ctypes import *
import os
c_int_p    = POINTER(c_int)
if os.path.exists("Biblio.dll"):
   bibo= windll.LoadLibrary("Biblio.dll") #path of dll file
    def hello(a):
        hello = bibo.hello     #select function in dll
        hello.argtypes =[c_int_p]
        hello.restype = c_int
        a  = c_int(a)
        return hello(byref(a))
else:
    print 'biblio.dll is not available'
lunar

@liddokun88: Beim gezeigten Quelltext muss die Bibliothek im Arbeitsverzeichnis des Programms liegen. Ich nehme mal an, dass Du beim Versuch mit einem anderen Modul das Programm aus einem anderen Verzeichnis heraus gestartet hast.
liddokun88
User
Beiträge: 18
Registriert: Montag 5. März 2012, 16:11

Vielen dank für die Nachricht. Hast mich auf die richtige Idee gebracht.

Das problem bestand darin, dass ich zwar das modul per

Code: Alles auswählen

import ABC
realisiert habe, jedoch habe ich einfach vergessen, dann die Abfrage der Funktionen in der dll mittels

Code: Alles auswählen

ABC.hello(a)
vorzunehmen.
Vielen Dank nochmal für die Info.
liddokun88
User
Beiträge: 18
Registriert: Montag 5. März 2012, 16:11

Eine Frage stellt sich mir da noch.

Momentan befindet sich meine ABC.py in dem Python Hauptordner (bei mir einfach C:\Python27). Ich möchte aber nicht unbedingt wenn das nun mehr Datein werden mit der Zeit alle in diesen Ordner speichern. Wenn ich sie allerdings in einen Unterordner verschiebe, so kann ich das Modul nicht mehr importieren von der Console. Gibt es einen Befehl der mir ermöglicht, dass das Programm auch in Unterordnern mein Modul sucht und findet?
lunar

Du kannst die Umgebungsvariable "$PYTHONPATH" setzen. Auf lange Sicht ist es allerdings sinnvoller, sich mit virtualenv sowie dem Standard-Python-Deployment in Form von distutils und distribute zu beschäftigen.
liddokun88
User
Beiträge: 18
Registriert: Montag 5. März 2012, 16:11

Bin dem Problem ein bischen näher gekommen. Habe zunächst mittels der funktion sys.path.append einen neuen Pfad hinzugefügt welchen er durchsuchen soll.

Code: Alles auswählen

import sys
sys.path.append('C:\Python27\ABC')
# ABC ist hierbei ein Ordner in dem sich die Datein befinden sollen
Ich stelle fest, dass das Problem in der Abfrage des Pfades liegt, wenn ich nun die ABC.py über die Console mittels des Befehls import versuche zu importieren

Code: Alles auswählen

import os
path = os.getcwd()   # sollte mir den Pfad angeben
if os.path.exists(os.path.join(path,"Biblio.dll")):
Das Problem besteht wie mir scheint darin, dass path nicht den Pfad der Datei wiedergibt, welche ich mit import versuche zu importieren, sondern einen anderen Pfad. Gibt es eine möglichkeit, den Pfad der aufgerufenen Datei zu bestimmen?
BlackJack

@liddokun88: Python-Module haben ein `__file__`-Attribut das man mit den entsprechenden Funktionen aus `os.path` auseinander nehmen kann.
Benutzeravatar
snafu
User
Beiträge: 6833
Registriert: Donnerstag 21. Februar 2008, 17:31
Wohnort: Gelsenkirchen

liddokun88 hat geschrieben:Gibt es eine möglichkeit, den Pfad der aufgerufenen Datei zu bestimmen?

Code: Alles auswählen

modulname.__file__
liddokun88
User
Beiträge: 18
Registriert: Montag 5. März 2012, 16:11

ok hab erstmal eine Lösung, auch wenn sie nicht sehr ellegant ist muss ich sagen. Mit __file__ konnte ich nicht arbeiten, die Console gab mir da stets zurück das sie __file__ nicht kennen würde.

Code: Alles auswählen

import sys
import os
from ctypes import *

sys.path.append('C:\Python27\ABC')
pathname = sys.path[8]  

if os.path.exists(os.path.join(pathname,"Biblio.dll")):
   
Der Haken ist, das ich hier davon ausgehe das auf der Position 8 der Pfad steht, leider habe ich da keine Idee ob man das nicht auch irgendwie anders lösen kann. Der Befehl sys.path.append('Pfad'), kann in meiner Variante auch über die Console eingegeben werden.
BlackJack

@liddokun88: Bei welchem Modul hast Du das denn versucht? Nicht jedes Modul wird aus einer Datei geladen und folglich haben auch nicht alle ein `__file__`-Attribut.

Wobei mir das Anhängen an `sys.path` um dann aus `sys.path` den Pfad wieder heraus zu holen irgendwie unnötig umständlich vorkommt. Die absolute Pfadangabe ist auch unschön. Man muss in dem Modul etwas ändern wenn das Ganze mal wo anders als nach ``C:\Python27\ABC\`` kopiert (”installiert”) wurde. Eigenen Code würde ich gar nicht unter ``C:\Python{version}\`` ablegen, ausser er wurde ordentlich über die vorgesehenen Mechanismen dort installiert.

Die ``if``-Abfrage nach der Existenz der Datei ist übrigens unschön, es sei denn im ``else``-Zweig kann irgendwie ausgeglichen werden, dass es die Datei nicht gibt. Aber selbst dann würde ich wohl einfach die entsprechende Ausnahme behandeln.
liddokun88
User
Beiträge: 18
Registriert: Montag 5. März 2012, 16:11

ist eine selbsgeschriebene Datei, die mehrere definierte Funktionen enthält.
An sich könnte ich das auch wo anders hinspeichern, das problem ist nur, dass das Programm meine
.dll einfach nicht finden will, es sei den ich gebe ihm irgendwie direkt den Pfad an.
Auf Die .dll soll später von aussen nicht mehr direkt zugegriffen werden; sondern lediglich einmal
beim starten von Python importiert werden.
Benutzeravatar
snafu
User
Beiträge: 6833
Registriert: Donnerstag 21. Februar 2008, 17:31
Wohnort: Gelsenkirchen

liddokun88 hat geschrieben:

Code: Alles auswählen

sys.path.append('C:\Python27\ABC')
pathname = sys.path[8]
Für das letzte Element einer Liste kann man auch `-1` als Indexwert setzen, anstatt der `8`.

Zudem: Wenn du den Pfad kurz zuvor angehangen hast, brauchst du doch das Element garnicht mehr abzufragen. Ein `path = r'C:\Python27\ABC'`, um dann darauf zu arbeiten, ginge genau so.

Hast du eigentlich schon das offizielle Python-Tutorial durchgearbeitet? Dir scheint es erheblich an Grundlagenwisse zu mangeln.
liddokun88
User
Beiträge: 18
Registriert: Montag 5. März 2012, 16:11

gebe zu hab ich nicht gemacht, muss diese Anbindung schnellst möglichst fertig bekommen,
gibt noch ne Menge andere Arbeit hier leider :)

Aber der Tip mit der -1 gefällt mir schonmal sehr.
Benutzeravatar
snafu
User
Beiträge: 6833
Registriert: Donnerstag 21. Februar 2008, 17:31
Wohnort: Gelsenkirchen

liddokun88 hat geschrieben:muss diese Anbindung schnellst möglichst fertig bekommen,
gibt noch ne Menge andere Arbeit hier leider :)
Das sind natürlich immer die besten Erfolgsaussichten und falls das für ne Firma ist, dann wird's da sicherlich bald noch großen Spass geben. Aber nunja, ich will dich nicht voll labern. :mrgreen:
liddokun88
User
Beiträge: 18
Registriert: Montag 5. März 2012, 16:11

Sagen wir es gibt immer viel zu tun :mrgreen:

Wie dem auch sei, hab was hübsches gefunden mit dem man das ganze noch ein bischen verkürzen kann. Ich habe hierfür einfach den Befehl

Code: Alles auswählen

import sys
sys.path.append('C:\Python27\ABC')
in eine Datei mit Namen sitecustomize.py in den Ordner C:\Python27\Lib\site-packages gespeichert. Der nette Effekt ist, das nun bei jedem neustarten von Python automatisch dieser Befehl mit ausgeführt wird, und damit zur verfügung steht.
liddokun88
User
Beiträge: 18
Registriert: Montag 5. März 2012, 16:11

ok habe eine Lösung gefunden die nun auch funktioniert.

wie bereits gesagt habe ich zunächst eine Datei geschrieben welche mir immer beim starten von Python das Verzeichniss in dem sich meine Datein befinden mit gibt. Im Anschluss verwende ich die funktion

Code: Alles auswählen

os.path.dirname(os.path.abspath(__file__))
um den Namen des "aktuellen" Ordners zu bestimmen. Danach kann ich einfach mittels der os.join funktion den gewünschten vollständigen Pfad angeben.

Vielen Dank nochmal für die Hilfe :idea:
Antworten