7 начина да проверите дали файл или папка съществуват в Python

Стандартната библиотека на Python съдържа по-голямата част от функционалността, необходима на разработчика, за да разреши проблем. В този урок ще научите различни начини за проверка на съществуването на файл или директория, като използвате само вградени модули.

Проверката дали даден файл или скрипт е на правилното място е от решаващо значение за всяка CLI програма. Вашата програма може да стане безполезна, ако определен файл не е на мястото си в момента на изпълнение.

В днешния урок ще научите някои бързи начини да проверите дали файл или папка съществува в Python.

Преди започване

Преди да изпълните която и да е команда по-долу, уверете се, че имате инсталиран Python 3 във вашата система. Отворете вашия терминал и въведете следната команда:

python --version
# Python 3.9.5, my result

Ако имате версия 2.x, ще трябва да използвате командата “python3”. Вижте нашето ръководство за инсталиране на Python, ако нямате инсталиран Python 3.

Ще използваме някои тестови файлове заедно с този урок, така че не забравяйте да създадете следните файлове:

touch testfile.txt
mkdir testdirectory/ 
touch testdirectory/otherfile.txt

Командите по-горе създават файл, с който да играете, директория за тестване и друг файл в директорията за тестване. Файловете могат да бъдат празни, тъй като няма да е необходимо да четем съдържанието им,

Забележка: Ако използвате Windows, настройте тази файлова проста файлова структура с графичен файлов мениджър.

Накрая ще използваме Ipython като нашата интерактивна обвивка на Python, която предоставя красив интерфейс за работа. Това е само стока, следователно не е строго необходимо.

pip install ipython

След като направите това, ще получите достъп до красива обвивка на Python, просто като напишете ipython.

Вече сте готови, нека се потопим в начините за проверка дали папка или файл съществува в Python.

Опитайте, Отворете и Освен

Това е най-простият вариант. Ако се опитате да отворите файл, който не съществува, Python ще повдигне a FileNotFoundError.

In [1]: open('im-not-here.txt')
---------------------------------------------------------------------------
FileNotFoundError: [Errno 2] No such file or directory: 'im-not-here.txt'

Можем да се възползваме от това и да обработим изключението, в случай че файлът, който търсим, не съществува.

In [2]: try:
   ...:     file = open('im-not-here.txt')
   ...:     print(file) # File handler
   ...:     file.close()
   ...: except FileNotFoundError:
   ...:     print('Sorry the file we're looking for doesn' exist')
   ...:     exit()
   ...: 
Sorry the file we're looking for doesn't exist

В кода по-горе ние отпечатваме персонализирано съобщение и спираме изпълнението на програмата, ако файлът не съществува.

  Как да промените снимката за групов разговор в съобщения на iPhone и iPad

Обърнете внимание как функцията exit() ще се изпълни само ако бъде повдигнато изключение. Нека да видим какво се случва, когато файлът, който търсим, действително съществува.

In [2]: try:
   ...:     file = open('testfile.txt')
   ...:     print(file) # File handler
   ...:     file.close()
   ...: except FileNotFoundError:
   ...:     print('Sorry the file we're looking for doesn't exist')
   ...:     exit()
   ...: 
<_io.TextIOWrapper name="testfile.txt" mode="r" encoding='UTF-8'>

Забележете как затваряме файла веднага след като сме го отворили. Счита се за добра практика според Документация на Python.

Извикване на file.write() без използване на ключовата дума with или извикване на file.close() може да доведе до това, че аргументите на file.write() не са напълно записани на диска, дори ако програмата излезе успешно.

Дори и да не пишем във файла, изключително препоръчително е да затворите файла, защото това може да доведе до множество проблеми с производителността.

Ако не искаме да затворим файла сами, можем да използваме контекстния мениджър с. Той разпределя и освобождава ресурси прецизно, следователно няма да е необходимо да затваряме файла.

In [3]: try:
   ...:     with open('testfile.txt') as file:
   ...:         print(file)
   ...:         # No need to close the file
   ...: except FileNotFoundError:
   ...:     print('Sorry the file we're looking for doesn't exist')
   ...:     exit()
   ...: 
   ...: 
<_io.TextIOWrapper name="testfile.txt" mode="r" encoding='UTF-8'>

Този метод е изключително полезен при писане във файлове, но води до неефективност, ако искаме само да проверим дали файлът съществува. Нека се потопим в други възможности за постигане на това.

os.path.exists()

The os модул осигурява множество функции за взаимодействие с оперативната система. За да проверим дали файл или папка съществува, можем да използваме функцията path.exists(), която приема пътя до файла или директорията като аргумент. Връща булево значение въз основа на съществуването на пътя.

Забележка: Пътят е уникалното местоположение на файл или директория във файлова система

В Python, ос.път подмодулът съдържа функции, предназначени изключително за работа с файлови пътища. Всички тези функции приемат аргумента на пътя като низове или байтове и можете да решите да работите с абсолютни пътища, например:

/home/daniel/.bashrc

Или с относителни пътища, в зависимост от директорията, в която изпълнявате скрипта:

.bashrc
# Running the script in my home folder

Ето няколко примера за използване на функцията os.path.exists(), работеща в директорията, в която се намират моите тестови файлове:

In [1]: import os

In [2]: os.path.exists('testfile.txt')
Out[2]: True

In [3]: os.path.exists('testdirectory')
Out[3]: True

In [4]: os.path.exists('hey-i-dont-exist')
Out[4]: False

Както можете да видите, той връща True, когато тества с файла testfile.txt и папката testdirectory, и False, когато файлът не съществува.

  Как да инсталирате Microsoft Teredo Tunneling Adapter

os.path.isfile()

Ако искате да докажете само съществуването на файл (а не на директория), бихте извикали функцията os.path.isfile().

In [1]: import os

In [2]: os.path.isfile('testfile.txt')
Out[2]: True

In [3]: os.path.isfile('testdirectory/')
Out[3]: False

In [4]: os.path.isfile('i-dont-even-exist')
Out[4]: False

In [5]: os.path.isfile('testdirectory/otherfile.txt')
Out[5]: True

Забележка: В UNIX всички директории завършват с наклонена черта (/), докато в Windows използваме обратна наклонена черта ().

В кода по-горе функцията isfile() връща False в два случая, нека видим защо:

  • testdirectory/ е директория, следователно не се счита за файл. Това не е абсолютно вярно, тъй като в Linux всичко е файлов дескрипторно Python третира директориите по различен начин само за удобство (Ако се опитате да отворите директория, ще получите IsADirectoryError)
  • i-dont-even-exist сочи към файл, който по ирония на съдбата не съществува

os.path.isdir()

Ако искате да проверите дали дадена директория е на правилното място, ще трябва да използвате функцията os.path.isdir(), която връща True само ако дадения път сочи към директория.

In [1]: import os

In [2]: os.path.isdir('testfile.txt')
Out[2]: False

In [3]: os.path.isdir('testdirectory')
Out[3]: True

In [4]: os.path.isdir('anotherfile.txt')
Out[4]: False

Обърнете внимание как примерите по-горе връщат False дори когато пътят сочи към файл, който съществува.

Глоб

The глоб модул предоставя функции за работа Модели, подобни на обвивка на Unix (следователно не работи правилно на Windows). За да проверите дали даден файл съответства на модел в текущата директория, можете да използвате glob.glob() функция.

In [1]: import glob

In [2]: glob.glob('testfile.txt')
Out[2]: ['testfile.txt']

In [3]: glob.glob('testdirectory')
Out[3]: ['testdirectory']

В кода по-горе моделът, предаван на функцията glob, е нормален низ, който представлява пътя до тестовия файл и директория. Тъй като съществуват и двата пътя, функцията връща списък със съответстващите имена на пътища вътре в него.

Забележка: Ако моделът не съвпада, ще получите празен списък.

Имайки предвид, че можем да предаваме модели към функцията glob, защо не изпробваме някои от основните й предимства?

Кодът по-долу получава всички файлови пътища с разширение съответно .txt и .py:

In [4]: glob.glob('*.txt')
Out[4]: ['testfile.txt']

In [5]: glob.glob('*.py')
Out[5]: 
['pathlib-exists.py',
 'list-dir.py',
 'glob-file.py',
 'open-except.py',
 'subprocess-test.py',
 'isfile.py',
 'exists.py',
 'isdir.py']

Използване на клас път

The Клас път е един от най-добрите начини за работа с пътеки, тъй като ни дава чист интерфейс за работа с пътеките на файлове като обекти.

  Как да деактивирате лентата за изтегляния в Chrome

Черешката на тортата е, че екземплярите на Path имат всички методи, от които се нуждаете, за да получите информация за определен път. Това включва функции, подобни на предишните опции.

Забележка: Ще ви трябва Python 3.4 или по-нова версия, за да използвате библиотеката pathlib

Методите на Path, които ще използвате:

Проверете дали съществува път

In [1]: from pathlib import Path

In [2]: Path('testfile.txt').exists()
Out[2]: True

In [3]: Path('im-not-here.txt').exists()
Out[3]: False

In [4]: Path('testdirectory').exists()
Out[4]: True

Работи по същия начин като os.path.exists().

Проверете дали пътят сочи към файл

In [5]: Path('testfile.txt').is_file()
Out[5]: True

In [6]: Path('testdirectory').is_file()
Out[6]: False

Еквивалентно на os.path.isfile().

Проверете дали пътят сочи към директория

In [7]: Path('testfile.txt').is_dir()
Out[7]: False

In [8]: Path('testdirectory').is_dir()
Out[8]: True

Съответства на os.path.isdir().

подпроцес

Ако сте любител на модулите за подпроцеси, ще трябва да знаете за тази опция. Можете да определите дали файл или папка съществува, като използвате тестова команда.

Забележка: Командата test работи само в Unix.

Следните тестови флагове ще свършат работата:

  • test -e: Проверете дали съществува път
  • test -f: Проверете дали файлът съществува
  • test-d: Проверете дали папка съществува

В случай, че искате да се потопите в повече тестови флагове, можете да прочетете ръководството, като стартирате:

man test

Проверка на път с подпроцес:

Кодът по-долу определя дали съществува път чрез сравняване на върнатия код на подпроцеса с 0.

Не забравяйте, че в Linux, ако даден процес е минал добре, той ще върне нула, ако не е, ще върне друг код.

In [1]: from subprocess import run

In [2]: run(['test', '-e', 'testfile.txt']).returncode == 0
Out[2]: True

In [3]: run(['test', '-e', 'im-not-here.txt']).returncode == 0
Out[3]: False

В първия оператор импортираме модула на подпроцеса, след което използваме изпълнява функция и получаване на неговия код за връщане.

Проверка на съществуването на файл с подпроцес

In [4]: run(['test', '-f', 'testfile.txt']).returncode == 0
Out[4]: True

In [5]: run(['test', '-f', 'testdirectory']).returncode == 0
Out[5]: False

Проверка на директория с подпроцес:

In [6]: run(['test', '-d', 'testfile.txt']).returncode == 0
Out[6]: False

In [7]: run(['test', '-d', 'testdirectory']).returncode == 0
Out[7]: True

Не е препоръчително да използвате тази опция, тъй като консумира повече ресурси и не получаваме никакви предимства от нея.

Да обобщим

Python е един от най-използваните езици за програмиране за автоматизиране на процеси чрез взаимодействие с операционната система. Едно страхотно нещо, което можете да направите с него, е да проверите дали файл или папка съществува.

Най-лесните за това са:

  • Отваряне и обработка на изключения на файлове веднага
  • Използване на функцията exists() на модулите os.path или pathlib.

В този урок научихте:

  • Как да отворите файл и да обработите изключения, в случай че не съществува
  • Значението на пътеките
  • 3 различни функции, които подмодулът os.path предоставя за проверка на съществуването на файл или папка
  • Unix използва наклонени черти (/), докато Windows използва наклонени черти ()

Следващо четене: Какво е подпроцес в Python? [5 Usage Examples]