Я пытаюсь, чтобы модуль внутри пакета открывал текстовый файл внутри своего каталога и читал его содержимое.

Вот как выглядит моя аранжировка:

package
|  __init__.py
|  bar.py
|  baz.py
|  txt.txt

foo.py

Это содержание txt.txt

a()

Это содержание baz.py

def a():
    with open("txt.txt") as file:
        print(file.read())

Это содержание bar.py

from .baz import a
def b():
    a()
    print("b()")

Это содержание __init__.py

from .bar import b
def c():
    b()
    print("c()")

Это содержание foo.py

from package import c
c()

При запуске foo.py я ожидал получить

a()
b()
c()

Но вместо этого я получил эту ошибку

Traceback (most recent call last):
  File "foo.py", line 2, in <module>
    c()
  File "(...my full path...)\package\__init__.py", line 3, in c
    b()
  File "(...my full path...)\package\bar.py", line 3, in b
    a()
  File "(...my full path...)\package\baz.py", line 2, in a
    with open("txt.txt") as file:
FileNotFoundError: [Errno 2] No such file or directory: 'txt.txt'

Я изменил аргумент функции open "txt.txt" на полный путь, и он работал, но это не очень полезно, потому что я должен использовать относительный путь, и я не понимаю, что происходит ,

Какие-либо предложения?

1
GT 77 20 Апр 2019 в 13:15

2 ответа

Лучший ответ

В Python пути относительно вызывающего скрипта в этом случае foo.py.

Если вы хотите прочитать txt.txt из вызова foo.py, вам нужно изменить baz.py следующим образом

def a():
    with open("package/txt.txt") as file:
        print(file.read())

Кроме того, вы можете получить путь к пакету с помощью os и sys вот так

import os
import sys
def a():
    with open(os.path.join(os.path.dirname(sys.modules[__name__].__file__),"txt.txt")) as file:
        print(file.read())
1
gawdn 20 Апр 2019 в 10:26

Вы можете установить переменную среды PYTHONPATH так, чтобы она указывала на ваш пакет, или вы можете указать txt.txt относительно того места, где вы запускаете foo.py

Для первого варианта вы можете сделать следующее: {{Х0}} для второго варианта сначала измените каталог на пакет, затем запустите foo.py

1
NaWeeD 20 Апр 2019 в 10:28