Saya sedang membangun skrip pembantu sederhana untuk pekerjaan yang akan menyalin beberapa file template di basis kode kami ke direktori saat ini. Namun, saya tidak memiliki jalur absolut ke direktori tempat templat disimpan. Saya memang memiliki jalur relatif dari skrip tetapi ketika saya memanggil skrip itu memperlakukannya sebagai jalur relatif ke direktori kerja saat ini. Apakah ada cara untuk menentukan bahwa url relatif ini berasal dari lokasi skrip?
python
relative-path
path
baudtack
sumber
sumber
Jawaban:
Di file yang memiliki skrip, Anda ingin melakukan sesuatu seperti ini:
Ini akan memberi Anda jalur absolut ke file yang Anda cari. Perhatikan bahwa jika Anda menggunakan setuptools, Anda sebaiknya menggunakan API sumber daya paketnya .
UPDATE : Saya menanggapi komentar di sini sehingga saya dapat menempelkan contoh kode. :-)
Saya berasumsi maksud Anda
__main__
skrip ketika Anda menyebutkan menjalankan file secara langsung. Jika demikian, sepertinya tidak demikian halnya pada sistem saya (python 2.5.1 pada OS X 10.5.7):Namun, saya tahu bahwa ada beberapa kebiasaan dengan
__file__
ekstensi C. Misalnya, saya bisa melakukan ini di Mac saya:Namun, ini menimbulkan pengecualian pada mesin Windows saya.
sumber
filename = os.path.join(dir, 'relative', 'path', 'to', 'file', 'you' , 'want')
os.path.dirname(__file__)
dapat memberikan string kosong, gunakanos.path.dirname(os.path.abspath(__file__))
sebagai gantinyayang Anda butuhkan
os.path.realpath
(contoh di bawah ini menambahkan direktori induk ke jalur Anda)sumber
os.path.dirname(__file__)
memberiku string kosong. Ini bekerja dengan sempurna.os.path.realpath('..')
memberi Anda direktori induk dari direktori kerja saat ini . Itu biasanya bukan yang Anda inginkan.Seperti disebutkan dalam jawaban yang diterima
Saya hanya ingin menambahkan itu
Seharusnya seperti itu
Jawaban yang diterima dapat menyesatkan dalam beberapa kasus, silakan lihat tautan ini untuk detailnya
sumber
os.path.join
lebih baik karena bergabung dengan mereka dengan pemisah khusus OS.'/relative/path...'
bukan jalan relatif. Apakah itu disengaja?os.path.join()
. Yang tersisa adalah preferensi untuk menggunakan string yang terpisah untuk setiap elemen path daripada hardcoding pemisah path.Sekarang tahun 2018, dan Python telah berevolusi sejak
__future__
lama. Jadi bagaimana menggunakan menakjubkanpathlib
datang dengan Python 3.4 untuk menyelesaikan tugas bukannya berjuang denganos
,os.path
,glob
,shutil
, dllJadi kami memiliki 3 jalur di sini (mungkin digandakan):
mod_path
: yang merupakan jalur skrip pembantu sederhanasrc_path
: yang berisi beberapa file templat yang menunggu untuk disalin.cwd
: direktori saat ini , tujuan dari file templat tersebut.dan masalahnya adalah: kita tidak memiliki path lengkap
src_path
, hanya tahu itu path relatif kemod_path
.Sekarang mari kita selesaikan ini dengan yang menakjubkan
pathlib
:Di masa depan, sesederhana itu. : D
Selain itu, kami dapat memilih dan memeriksa dan menyalin / memindahkan file templat tersebut dengan
pathlib
:sumber
Pertimbangkan kode saya:
sumber
Lihat sys.path Seperti diinisialisasi pada startup program, item pertama dari daftar ini, path [0], adalah direktori yang berisi skrip yang digunakan untuk memanggil juru bahasa Python.
Gunakan jalur ini sebagai folder root tempat Anda menerapkan jalur relatif Anda
sumber
sys.path[0]
tidak selalu disetel ke direktori induk. Kode python dapat dipanggil dengan-c
atau-m
melalui interpreter yang disematkan, pada titik manasys.path[0]
diatur ke sesuatu yang berbeda sama sekali.Alih-alih menggunakan
seperti pada jawaban yang diterima, akan lebih kuat untuk digunakan:
karena menggunakan __file__ akan mengembalikan file dari mana modul dimuat, jika itu diambil dari file, jadi jika file dengan skrip dipanggil dari tempat lain, direktori yang dikembalikan tidak akan benar.
Jawaban ini memberikan detail lebih lanjut: https://stackoverflow.com/a/31867043/5542253 dan https://stackoverflow.com/a/50502/5542253
sumber
inspect.stack()
adalah fungsi yang mahal untuk dipanggil. Ini mengambil info untuk semua frame stack, yang kemudian Anda buang dan hanya mendapatkan yang teratas untuk. Ini pada dasarnya memanggilinspect.getfile()
objek modul, yang baru saja kembalimodule.__file__
. Anda jauh lebih baik dari hanya menggunakan__file__
.Hai pertama-tama Anda harus memahami fungsi os.path.abspath (path) dan os.path.relpath (path)
Singkatnya os.path.abspath (path) membuat jalur relatif ke jalur absolut . Dan jika jalur yang disediakan itu sendiri merupakan jalur absolut maka fungsinya mengembalikan jalur yang sama.
sama os.path.relpath (path) membuat path absolut ke path relatif . Dan jika jalur yang disediakan itu sendiri merupakan jalur relatif maka fungsinya mengembalikan jalur yang sama.
Contoh di bawah ini memungkinkan Anda memahami konsep di atas dengan benar :
misalkan saya punya file input_file_list.txt yang berisi daftar file input yang akan diproses oleh skrip python saya.
D: \ conc \ input1.dic
D: \ conc \ input2.dic
D: \ Copyioconc \ input_file_list.txt
Jika Anda melihat struktur folder di atas, input_file_list.txt ada di folder Copyofconc dan file yang akan diproses oleh skrip python ada di folder conc
Tetapi isi file input_file_list.txt adalah seperti yang ditunjukkan di bawah ini:
.. \ conc \ input1.dic
.. \ conc \ input2.dic
Dan skrip python saya hadir di D: drive.
Dan jalur relatif yang disediakan dalam file input_file_list.txt relatif terhadap jalur file input_file_list.txt .
Jadi ketika skrip python akan mengeksekusi direktori kerja saat ini (gunakan os.getcwd () untuk mendapatkan path)
Karena jalur relatif saya relatif ke input_file_list.txt , yaitu "D: \ Copyofconc" , saya harus mengubah direktori kerja saat ini menjadi "D: \ Copyofconc" .
Jadi saya harus menggunakan os.chdir ('D: \ Copyofconc') , jadi direktori kerja saat ini adalah "D: \ Copyofconc" .
Sekarang untuk mendapatkan file input1.dic dan input2.dic , saya akan membaca baris ".. \ conc \ input1.dic" maka akan menggunakan perintah
input1_path = os.path.abspath ('.. \ conc \ input1.dic') (untuk mengubah path relatif ke path absolut. Di sini sebagai direktori kerja saat ini adalah "D: \ Copyofconc", file ". \ conc \ input1. dic "harus diakses relatif ke" D: \ Copyofconc ")
jadi input1_path akan menjadi "D: \ conc \ input1.dic"
sumber
Kode ini akan mengembalikan jalur absolut ke skrip utama.
Ini akan berfungsi bahkan dalam modul.
sumber
sys.modules['__main__'].__file__
.Alternatif yang bekerja untuk saya:
sumber
Apa yang berhasil untuk saya gunakan
sys.path.insert
. Lalu saya menentukan direktori yang harus saya kunjungi. Misalnya saya hanya perlu naik satu direktori.sumber
Saya tidak yakin apakah ini berlaku untuk beberapa versi yang lebih lama, tapi saya percaya Python 3.3 memiliki dukungan path relatif asli.
Misalnya kode berikut harus membuat file teks dalam folder yang sama dengan skrip python:
(perhatikan bahwa tidak boleh ada garis depan atau garis miring terbalik di awal jika itu jalan relatif)
sumber