Операции проверки файлов
Перед выполнением операций ввода-вывода часто требуется узнать информацию об объектах файловой системы. В Perl есть наборунарных операций для удобной проверки различных характеристик файлов и каталогов. Они имеют вид флагов из одной латинской буквы с предшествующим знаком минус, после которого указывается имя проверяемого файла. Полный перечень операций проверки файлов приведен в таблице 9.3.
Таблица 9.3. Операции проверки файлов
Операции |
Описание проверок |
-r -w -x |
Файл доступен для чтения / записи / исполнения (по effective UID+GID) |
-R -W -X |
Файл доступен для чтения / записи / исполнения (по real UID+GID) |
-o -O |
Файл принадлежит текущему пользователю по effective / real UID |
-e -z |
Файл существует (exists) / имеет нулевую длину (zero) |
-s |
Файл имеет ненулевой размер: возвращает размер в байтах (size) |
-f -d |
Файл является обычным файлом (file) / каталогом (directory) |
-l -S -p |
Файл является ссылкой / сокетом / именованным FIFO-каналом (pipe) |
-b -c |
Файл является блочным / символьным специальным файлом |
-u -g -k |
Для файла установлен бит setuid / setgid / sticky |
-t |
Файловый манипулятор связан с терминалом (tty) |
-T -B |
Файл является текстовым (text) / двоичным (binary) |
-M -A -C |
Время изменения (modification) / доступа (access) / изменения (change) индексного узла (inode) файла в днях относительно времени начала выполнения программы ($^T) |
Вот несколько типичных примеров использования операций проверки файлов для контроля доступности данных:
open($f1, "<$file1") # открыть файл на чтение,
if (-e $file1) && # если он существует и
(-r $file1); # он доступен на чтение
open $f2, ">$file2" # открыть файл на запись,
if -w $file2; # если в него можно писать
$file_size = -s $file; # узнать размер файла
print "$file - является каталогом!" if -d $file;
Функции работы с файлами
В Perl есть целый набор встроенных функций для работы с файлами, с помощью которых можно манипулировать с самимифайлами, а не с данными, хранящимися в них.
Функция rename() переименовывает файл, возвращая логическое значение: 1 при успешном изменении имени и 0 - в противном случае. Ей передаются старое и новое имя файла с абсолютным или относительным путем.
$ok = rename("$path/$old_name", "$path/$new_name");
Функция unlink() удаляет файл или список файлов, возвращая число 1 при успешном удалении и 0 - при ошибке.
unlink($list, $of, $files); # удалить список файлов
unlink $file if -e $file; # удалить файл, если он существует
Функция truncate() усекает файл до указанного размера и возвращает число 1 в случае успешного выполнения усечения инеопределенное значение undef - при возникновении ошибки. Файл может задаваться именем или файловым манипулятором. Например:
$ok = truncate($file, $size);
Функция stat() возвращает информацию о файле в виде списка или пустой список при неудаче. Файл может задаваться манипулятором файла или выражением со значением имени файла:
@info = stat($file); # получить всю информацию о файле
$size = $info[7]; # размер файла в байтах
$modified = localtime($info[9]); # время изменения файла
Подробное описание всех элементов информационного списка можно найти в документации, указав утилите чтения документовимя функции следующим образом:
Функция utime() изменяет у файла (или нескольких файлов из заданного списка) время доступа и время модификации, задаваемые числовыми значениями.
utime($access_time, $modified_time, @list_of_files);
Кроме упомянутых, есть еще встроенные функции для изменения прав доступа и владельца файла, для чтения и создания символических и жестких ссылок. Немало разных функций для работы с файлами имеются в стандартной библиотеке модулейPerl, еще больше можно найти в хранилище модулей CPAN.
Функции работы с каталогами
Помимо работы с файлами, в Perl есть необходимый набор встроенных функций для работы с каталогами. Нужно иметь в виду, что успешность выполнения операций с каталогами зависит от набора прав пользователя, от лица которого выполняется Perl-программа.
Функция mkdir() создает каталог с указанным именем. Вторым аргументом функции можно задавать права доступа для создаваемого каталога (в соответствии со стандартом POSIX). Возвращает число 1 при успешном создании или 0 при ошибке.Причину неудачи при создании каталога можно узнать из специальной переменной $!, которая содержит сообщение об ошибке.
$ok = mkdir $directory_name; # создать каталог
mkdir $dir, $access_rights; # создать каталог, задав права
Функция rmdir() удаляет каталог по его имени, если он пуст, возвращает число 1 при успешном удалении каталога или 0 в случае ошибки. Тогда из переменной $! можно выяснить подробности неудачи:
$ok = rmdir $directory_name; # удалить каталог
Функция chdir() изменяет текущий каталог на значение строкового выражения, содержащего имя нового текущего каталога. Если имя каталога не задано, она переходит в домашний каталог пользователя, используя значение элемента $ENV{"HOME"} или$ENV{"LOGNAME"} из специального хэша %ENV, который содержит значения переменных окружения операционной системы. Возвращает число 1 при успешном переходе в другой каталог или 0 в случае возникновения ошибки.
$ok = chdir $new_dir; # перейти в каталог $new_dir
chdir; # перейти в домашний каталог
Много других возможностей по работе с каталогами предоставляют функции из стандартной библиотеки модулей Perl. Например,функция cwd() из стандартного модуля Cwd возвращает имя текущего (рабочего) каталога во время выполнения программы:
use Cwd; # подключить библиотечный модуль Cwd
my $current_work_directory = cwd; # запросить текущий каталог
Иногда при выполнении программы нужно определить каталог, откуда она была запущена, чтобы организовать доступ к егоподкаталогам. Переменная Bin, устанавливаемая в модуле FindBin из стандартной библиотеки, содержит имя каталога, из которого программа была запущена, например:
use FindBin; # подключить библиотечный модуль FindBin
my $program_start_dir = $FindBin::Bin; # стартовый каталог
Perl также предоставляет набор функций, организующий чтение содержимого каталога, подобно чтению записей файла. Элементами каталога могут быть обыкновенные файлы и другие каталоги, включая вложенные подкаталоги, текущий каталог(обозначаемый одной точкой) и родительский каталог (обозначаемый двумя точками).
Перед чтением содержимого каталога его необходимо открыть. Функция opendir() открывает каталог по его имени и ассоциирует его с указанным манипулятором каталога. Функция возвращает число 1 при успешном открытии, undef - при неудаче. Вот так, например, открывается каталог и создается манипулятор каталога DIR_HANDLE:
$ok = opendir DIR_HANDLE, $directory_name;
Современный стиль программирования рекомендует при открытии каталога сохранять манипулятор каталога в скалярной переменной. Это ограничивает область его видимости текущим блоком или подпрограммой и предотвратит случайное изменениеманипулятора в других частях программы. Например, так:
$ok = opendir my $dir_handle, $directory_name;
Функция closedir() закрывает каталог, открытый функцией opendir(), используя манипулятор каталога. Возвращает число 1 при успешном закрытии или undef - при неудаче. Хотя открытые каталоги автоматически закрываются по окончании программы, рекомендуется все же делать это явно:
$ok = closedir $dir_handle; # закрыть каталог
Функция readdir() в скалярном контексте читает очередной элемент каталога, возвращая неопределенное значение undef, когда будет прочитан последний элемент. Например:
my $file_name = readdir $dir_handle;
Таким образом можно организовать обработку всех элементов каталога в цикле, исключая текущий и родительский каталоги:
while (my $file_name = readdir $dir_handle) {
if ($file_name ne '.' && $file_name ne '..') {
print "каталог $file_name\n" if -d $file_name;
print "файл $file_name\n" if -f $file_name;
}
}
В списочном контексте функция readdir() возвращает список всех элементов каталога, что часто бывает весьма удобно:
@file_names = readdir $dir_handle; # считать весь каталог
Иногда требуется, не закрывая каталога, начать его обработку сначала. Функция rewinddir() устанавливает позицию чтения в начало открытого каталога, после чего чтение начнется с первого элемента:
rewinddir $dir_handle; # 'перемотать' на начало каталога
Функция telldir() возвращает текущую позицию в каталоге, которую можно использовать для перемещения в эту позицию с помощью функции seekdir():
$dir_position = telldir $dir_handle; # позиция чтения
Используя возвращенное функцией telldir() значение, встроенная функция seekdir() устанавливает новую позицию для чтения каталога с помощью функции readdir():
seekdir $dir_handle, $dir_position; # вернуться к позиции
После изучения представленных в этой лекции средств ввода-вывода вполне можно писать законченные и полезные программы наPerl. Но пройдена только половина пути: в следующих лекциях курса будет рассказано о важных конструкциях и механизмах системы программирования Perl, без которых невозможно разрабатывать современные программы на профессиональном уровне.
|