Skip to content

Ermitteln des Pfades der aktuellen Datei (Skript) in Python: __file__

Python

In Python can SIE den Pfad (Speicherort) der aktuellen Datei, dh der aktuell ausgeführten Skriptdatei (.py) mit __file__ abrufen. __file__ ist nützlich, um andere Dateien basierend auf dem Speicherort der aktuellen Datei zu lesen.

In Python 3.8 und früher gibt es __file__ den Pfad zurück, der beim Ausführen des Befehls python (oder python3) angegeben wurde. Wenn SIE einen relativen Pfad angeben, wird ein relativer Pfad zurückgegeben. Wenn SIE einen absoluten Pfad angeben, wird ein absoluter Pfad zurückgegeben.

In Python 3.9 und höher gibt es __file__ immer einen absoluten Pfad zurück, unabhängig davon, ob der mit dem Python-Befehl angegebene Pfad relativ oder absolut ist.

Dieser Artikel hat folgenden Inhalt.

  • os.getcwd() und __file__
  • Rufen Sie den Datei- und Verzeichnisnamen der aktuellen Skriptdatei ab
  • Holen Sie sich den absoluten Pfad der aktuellen Skriptdatei
  • Lesen Sie andere Dateien basierend auf dem Speicherort der aktuellen Skriptdatei
  • Ändern Sie das aktuelle Verzeichnis in das Verzeichnis der aktuellen Skriptdatei
  • Lesen Sie dieselbe Datei unabhängig vom aktuellen Arbeitsverzeichnis

Im folgenden Artikel erfahren SIE, wie SIE das aktuelle Arbeitsverzeichnis abrufen und ändern.

Hinweis SIE, dass __file__ nicht in Jupyter Notebook (.ipynb) verwendet werden kann. Unabhängig vom Verzeichnis, in dem Jupyter Notebook gestartet WIRD, befindet sich .ipynb im aktuellen Verzeichnis. Es ist möglich, das aktuelle Verzeichnis mit os.chdir() im Code zu ändern.

os.getcwd() und __file__

Angenommen, SIE arbeiten im folgenden Verzeichnis. Unter Windows können Sie das aktuelle Verzeichnis mit dem Befehl dir anstelle von pwd überprüfen.

pwd
# /Users/mbp/Documents/my-project/python-snippets/notebook

Erstellen Sie eine Python-Skriptdatei (file_path.py) mit dem following Code im unteren Verzeichnis (data/src).

import os

print('getcwd:      ', os.getcwd())
print('__file__:    ', __file__)

Führen Sie es mit dem Befehl python (oder python3) aus.

python3 data/src/file_path.py
# getcwd:       /Users/mbp/Documents/my-project/python-snippets/notebook
# __file__:     data/src/file_path.py

Den absoluten Pfad des aktuellen Arbeitsverzeichnisses erhalten Sie mit os.getcwd() und den mit dem python3-Befehl angegebenen Pfad mit __file__.

In Python 3.8 und früher WIRD der durch den Befehl python (oder python3) angegebene Pfad in __file__ gespeichert. Im Beispiel wird ein relativer Pfad angegeben, also wird ein relativer Pfad zurückgegeben, aber wenn ein absoluter Pfad angegeben wird, wird ein absoluter Pfad zurückgegeben.

pwd
# /Users/mbp/Documents/my-project/python-snippets/notebook

python3 /Users/mbp/Documents/my-project/python-snippets/notebook/data/src/file_path.py
# getcwd:       /Users/mbp/Documents/my-project/python-snippets/notebook
# __file__:     /Users/mbp/Documents/my-project/python-snippets/notebook/data/src/file_path.py

In Python 3.9 und höher speichert __file__ immer einen absoluten Pfad, unabhängig davon, ob der mit dem Python-Befehl angegebene Pfad relativ oder absolut ist.

Fügen Sie in den folgenden Beispielen Code zu derselben Skriptdatei (file_path.py) hinzu und führen Sie sie aus demselben Verzeichnis wie im Beispiel in Python 3.7 aus.

Beachten Sie, dass, wenn __file__ ein absoluter Pfad ist (bei Python 3.9 oder höher oder bei Angabe des absoluten Pfads in Python 3.8 oder früher), Sie sehen Code wie unten beschrieben verwenden can, um andere Dateien basierend auf dem Speicherort der aktuellen Skriptdatei zu lesen . Die Ergebnisse der Ausführung durch Angabe des absoluten Pfads in Python3.7 werden am Ende angezeigt.

Rufen Sie den Datei- und Verzeichnisnamen der aktuellen Skriptdatei ab

Verwenden Sie os.path.basename() und os.path.dirname(), um den Datei- und Verzeichnisnamen der aktuellen Skriptdatei abzurufen.

print('basename:    ', os.path.basename(__file__))
print('dirname:     ', os.path.dirname(__file__))

Das Ergebnis ist wie folgt.

# basename:     file_path.py
# dirname:      data/src

Wenn Sie nur den Verzeichnisnamen direkt über der Datei erhalten möchten, verwenden Sie os.path.basename(os.path.dirname(__file__)).

Siehe den following Artikel für Details zu os.path.basename(), os.path.dirname() usw.

Holen Sie sich den absoluten Pfad der aktuellen Skriptdatei

Wenn Sie den relativen Pfad mit __file__ erhalten, können Sie ihn mit os.path.abspath() in einen absoluten Pfad umwandeln.

print('abspath:     ', os.path.abspath(__file__))
print('abs dirname: ', os.path.dirname(os.path.abspath(__file__)))

Das Ergebnis ist wie folgt.

# abspath:      /Users/mbp/Documents/my-project/python-snippets/notebook/data/src/file_path.py
# abs dirname:  /Users/mbp/Documents/my-project/python-snippets/notebook/data/src

Wenn Sie in os.path.abspath() einen absoluten Pfad angeben, wird dieser so zurückgegeben, wie er ist. Wenn also __file__ ein absoluter Pfad ist, wird kein Fehler ausgelöst, selbst wenn Sie os.path.abspath(__file__) festlegen.

Lesen Sie andere Dateien basierend auf dem Speicherort der aktuellen Skriptdatei

Wenn Sie andere Dateien basierend auf dem Speicherort (Pfad) der aktuellen Skriptdatei lesen möchten, verbinden Sie den Verzeichnispfad der aktuellen Datei und den relativen Pfad (von der aktuellen Datei) der Datei, die Sie lesen möchten, mit os.path. beitreten().

Beachten Sie, dass Dateien in demselben im Verzeichnis wie die Skriptdatei gelesen werden können, und nur der Dateiname angegeben WIRD.

print('[set target path 1]')
target_path_1 = os.path.join(os.path.dirname(__file__), 'target_1.txt')

print('target_path_1: ', target_path_1)

print('read target file:')
with open(target_path_1) as f:
    print(f.read())

Das Ergebnis ist wie folgt.

# [set target path 1]
# target_path_1:  data/src/target_1.txt
# read target file:
# !! This is "target_1.txt" !!

Das obere Verzeichnis WIRD DURCH ../ dargestellt. So wie es ist, gibt es kein Problem, aber wenn Sie os.path.normpath() verwenden, können Sie den Pfad normalisieren und zusätzliche ../ usw. entfernen.

print('[set target path 2]')
target_path_2 = os.path.join(os.path.dirname(__file__), '../dst/target_2.txt')

print('target_path_2: ', target_path_2)
print('normalize    : ', os.path.normpath(target_path_2))

print('read target file:')
with open(target_path_2) as f:
    print(f.read())

Das Ergebnis ist wie folgt.

# [set target path 2]
# target_path_2:  data/src/../dst/target_2.txt
# normalize    :  data/dst/target_2.txt
# read target file:
# !! This is "target_2.txt" !!

Ändern Sie das aktuelle Verzeichnis in das Verzeichnis der aktuellen Skriptdatei

Verwenden Sie os.chdir(), um das aktuelle Arbeitsverzeichnis in das Verzeichnis der aktuellen Skriptdatei zu ändern.

Sie können die Änderung mit os.getcwd() bestätigen.

print('[change directory]')
os.chdir(os.path.dirname(os.path.abspath(__file__)))
print('getcwd:      ', os.getcwd())

Das Ergebnis ist wie folgt.

# [change directory]
# getcwd:       /Users/mbp/Documents/my-project/python-snippets/notebook/data/src

Wenn das aktuelle Arbeitsverzeichnis mit dem Verzeichnis der aktuellen Datei identisch IST, können SIE einen relativen Pfad von der aktuellen Datei angeben, um andere Dateien zu lesen.

print('[set target path 1 (after chdir)]')
target_path_1 = 'target_1.txt'

print('target_path_1: ', target_path_1)

print('read target file:')
with open(target_path_1) as f:
    print(f.read())

print()
print('[set target path 2 (after chdir)]')
target_path_2 = '../dst/target_2.txt'

print('target_path_2: ', target_path_2)

print('read target file:')
with open(target_path_2) as f:
    print(f.read())

Das Ergebnis ist wie folgt.

# [set target path 1 (after chdir)]
# target_path_1:  target_1.txt
# read target file:
# !! This is "target_1.txt" !!
# 
# [set target path 2 (after chdir)]
# target_path_2:  ../dst/target_2.txt
# read target file:
# !! This is "target_2.txt" !!

Lesen Sie dieselbe Datei unabhängig vom aktuellen Arbeitsverzeichnis

Indem SIE __file__ verwenden, um den Pfad der aktuellen Skriptdatei abzurufen, can SIE dieselbe Datei unabhängig vom aktuellen Arbeitsverzeichnis lesen.

Wie bisher gezeigt, gibt es zwei Möglichkeiten:

  • Verbinden Sie das Verzeichnis __file__ und den relativen Pfad (von __file__) der Datei, die Sie lesen möchten, mit os.path.join().
  • Ändern Sie das aktuelle Arbeitsverzeichnis in das Verzeichnis __file__.

Es ist, das aktuelle Verzeichnis zu ändern, aber wenn SIE danach Dateien lesen oder schreiben, & SIE natürlich berücksichtigen, dass das aktuelle Verzeichnis geändert wurde.

Das Ergebnis der bisherigen Beispiele ist wie folgt.

pwd
# /Users/mbp/Documents/my-project/python-snippets/notebook

python3 data/src/file_path.py
# getcwd:       /Users/mbp/Documents/my-project/python-snippets/notebook
# __file__:     data/src/file_path.py
# basename:     file_path.py
# dirname:      data/src
# abspath:      /Users/mbp/Documents/my-project/python-snippets/notebook/data/src/file_path.py
# abs dirname:  /Users/mbp/Documents/my-project/python-snippets/notebook/data/src
# 
# [set target path 1]
# target_path_1:  data/src/target_1.txt
# read target file:
# !! This is "target_1.txt" !!
# 
# [set target path 2]
# target_path_2:  data/src/../dst/target_2.txt
# normalize    :  data/dst/target_2.txt
# read target file:
# !! This is "target_2.txt" !!
# 
# [change directory]
# getcwd:       /Users/mbp/Documents/my-project/python-snippets/notebook/data/src
# 
# [set target path 1 (after chdir)]
# target_path_1:  target_1.txt
# read target file:
# !! This is "target_1.txt" !!
# 
# [set target path 2 (after chdir)]
# target_path_2:  ../dst/target_2.txt
# read target file:
# !! This is "target_2.txt" !!

Das Ergebnis für die Angabe des absoluten Pfads mit dem Befehl python3 lautet wie folgt. Sie können dieselbe Datei lesen.

pwd
# /Users/mbp/Documents/my-project/python-snippets/notebook

python3 /Users/mbp/Documents/my-project/python-snippets/notebook/data/src/file_path.py
# getcwd:       /Users/mbp/Documents/my-project/python-snippets/notebook
# __file__:     /Users/mbp/Documents/my-project/python-snippets/notebook/data/src/file_path.py
# basename:     file_path.py
# dirname:      /Users/mbp/Documents/my-project/python-snippets/notebook/data/src
# abspath:      /Users/mbp/Documents/my-project/python-snippets/notebook/data/src/file_path.py
# abs dirname:  /Users/mbp/Documents/my-project/python-snippets/notebook/data/src
# 
# [set target path 1]
# target_path_1:  /Users/mbp/Documents/my-project/python-snippets/notebook/data/src/target_1.txt
# read target file:
# !! This is "target_1.txt" !!
# 
# [set target path 2]
# target_path_2:  /Users/mbp/Documents/my-project/python-snippets/notebook/data/src/../dst/target_2.txt
# normalize    :  /Users/mbp/Documents/my-project/python-snippets/notebook/data/dst/target_2.txt
# read target file:
# !! This is "target_2.txt" !!
# 
# [change directory]
# getcwd:       /Users/mbp/Documents/my-project/python-snippets/notebook/data/src
# 
# [set target path 1 (after chdir)]
# target_path_1:  target_1.txt
# read target file:
# !! This is "target_1.txt" !!
# 
# [set target path 2 (after chdir)]
# target_path_2:  ../dst/target_2.txt
# read target file:
# !! This is "target_2.txt" !!

Ändern Sie das aktuelle Verzeichnis im Terminal und führen Sie dieselbe Skriptdatei aus. Sie können sehen, dass dieselbe Datei von verschiedenen Orten gelesen wird.

cd data/src

pwd
# /Users/mbp/Documents/my-project/python-snippets/notebook/data/src

python3 file_path.py
# getcwd:       /Users/mbp/Documents/my-project/python-snippets/notebook/data/src
# __file__:     file_path.py
# basename:     file_path.py
# dirname:      
# abspath:      /Users/mbp/Documents/my-project/python-snippets/notebook/data/src/file_path.py
# abs dirname:  /Users/mbp/Documents/my-project/python-snippets/notebook/data/src
# 
# [set target path 1]
# target_path_1:  target_1.txt
# read target file:
# !! This is "target_1.txt" !!
# 
# [set target path 2]
# target_path_2:  ../dst/target_2.txt
# normalize    :  ../dst/target_2.txt
# read target file:
# !! This is "target_2.txt" !!
# 
# [change directory]
# getcwd:       /Users/mbp/Documents/my-project/python-snippets/notebook/data/src
# 
# [set target path 1 (after chdir)]
# target_path_1:  target_1.txt
# read target file:
# !! This is "target_1.txt" !!
# 
# [set target path 2 (after chdir)]
# target_path_2:  ../dst/target_2.txt
# read target file:
# !! This is "target_2.txt" !!