Вы находитесь на странице: 1из 8

Лекции курса PHP7 +MySQL с нуля

(краткое содержание)

ЛЕКЦИЯ 34. СТАНДАРТНЫЕ ФУНКЦИИ. РАБОТА С ФАЙЛАМИ.

PHP, как и другие современные языки программирования, позволяет


выполнять большое количество операций с файлами. В этой главе мы рассмотрим
основные стандартные функции, которые позволяют осуществлять операции
открытия, чтения, записи и закрытия файлов, а также некоторые особенности
работы этих функций.
Кроме того, следует упомянуть, что в PHP различия между ОС семейств
Windows и UNIX в синтаксисе путей файлов не имеют значения, т. к. интерпретатор
самостоятельно трансформирует пути в нужный вид. Речь идет о различии слешей
при указании пути: для Windows используется обратный слеш (\), в отличие от UNIX,
где используется прямой слеш (/). И все же, рекомендуется использовать везде
только прямой слеш при указании пути файла, чтобы исключить проблему
переносимости и чтения символов, т. к., например, сочетание символов /n в пути
файла будет воспринято, как специальный символ перехода на новую строку и
будет пропущено при выводе такой строки.
Также при работе с файлами есть особенность их чтения: в бинарном или
текстовом форматах. Этот момент будет рассмотрен далее в этом уроке.
Все представленные в уроке функции будут рассматриваться в комплексе и
будут приведены в едином листинге работы с файлом в конце урока.

Открытие файла
Перед тем как начать работу с файлом, его надо открыть (или установить с
ним соединение, если речь идет о файле, размещенном на другом компьютере, что
для PHP равносильно). Функция открытия файла fopen() имеет следующий
синтаксис:
int fopen(string $file, string $mode [, bool $use_include = false, resource $context])
Функция содержит следующие параметры:
1) $file – имя файла, содержащее полный абсолютный или относительный путь
к нему в случае, если файл располагается не в одной папке с файлом, содержащим
программный код его использования;
2) $mode – режим открытия файла, указывающий на ряд параметров работы с
файлом. Режимы открытия файла содержат следующие параметры:
Таблица 34.1. Режимы $mode при работе с файлом через функцию fopen()
Очистка Создание Ошибка
Режим Чтение Запись Указатель
файла файла наличия
r Да Нет В начале Нет Нет Нет
r+ Да Да В начале Нет Нет Нет
w Нет Да В начале Да Да Нет
w+ Да Да В начале Да Да Нет
a Нет Да В конце Нет Да Нет
a+ Да Да В конце Нет Да Нет
x Нет Да В начале Нет Да Да
x+ Да Да В начале Нет Да Да
c Нет Да В начале Нет Да Нет
c+ Да Да В начале Нет Да Нет

1
Лекции курса PHP7 +MySQL с нуля
(краткое содержание)

Таблица 34.2. Режимы чтения файла через функцию fopen()


Режим Тип режима
b Бинарный режим (учитывает символы окончания строк)
t Текстовый режим (не учитывает символы окончания строк)
Способ задания режима следующий:
- в первую очередь указывается режим работы с файлом;
- затем – режим чтения.
Следует указать, что режим чтения является не обязательным, но
рекомендуемым параметром. Если режим не указан явно, то будет использован
установленный по умолчанию в операционной системе, что может затруднить
переносимость на различные платформы.
Так, для примера, режим $mode может быть следующим – “r+b”.
3) Необязательный параметр $use_include в состоянии true указывает на
необходимость поиска открываемого файла также и в путях, указанных в
инструкциях include и require. Обычно не указывается.
4) Необязательный параметр $context используется при работе с файлами,
размещенными в сети и может содержать инструкции для такого файла, например,
значения из глобальной переменной $_SERVER, таких как USER_AGENT.

Различия бинарных и текстовых режимов


Ранее уже говорилось о важности различия между режимом чтения файла при
его открытии: бинарном или текстовом.
Различие их в следующем.
В зависимости от типа операционной системы, в конце каждой строки файла
размещаются символы окончания строки и перевода указателя на новую строку.
Так, для систем Windows используются символы \n\r, для Mac OS - \r\n, а для
семейства UNIX - \n.
Проблема может произойти при чтении файла, если будет произведен
перенос с одной ОС на другую, например, при открытии файла в операционных
системах Windows и UNIX количество символов при выводе содержимого каждой
строки будет различаться на один элемент - \r, что впоследствии может создать ряд
проблем при обработке кода.

Вспомогательные конструкции die() и exit()


При работе с файлами, как и с сетевыми соединениями, часто появляется
необходимость контролировать вывод ошибок на экран в случае их появления. Для
таких целей служит конструкция die(), которая по факту есть синоним конструкции
exit(), выводящей заданное сообщение на экран и прекращающая дальнейшее
выполнение программы.
Обычно используется в связке с оператором or, являющимся аналогом ||, но
имеющим более низкий приоритет.
Внутри скобок можно указывать как текстовые сообщения, так и другие
функции PHP, связанные с завершением кода программы, например,
определением типа полученной ошибки.

Закрытие файла
В PHP есть удобный инструмент «сбора мусора», который через
определенные промежутки времени производит сбор и очистку неиспользуемых

2
Лекции курса PHP7 +MySQL с нуля
(краткое содержание)

переменных, соединений, файлов и др. При этом стоит помнить, что происходит
это не часто и может сильно нагрузить память.
И все же не стоит ориентироваться только на автоматические возможности
PHP, особенно при работе с файлами и сетевыми соединениями.
Для закрытия файла и сетевого соединения с файлом определена функция
fclose():
int fclose(int $fp)
Закрывает файл, предварительно открытый функцией fopen(). В случае, если
закрыть файл не удалось, возвращает false.
Данная функция имеет более широкий спектр возможностей и может
закрывать соединения для других функций, не рассматриваемых в рамках этого
курса.

Блочные чтение и запись


Для операции чтения данных из файла используется функция fread(),
синтаксис которой представлен далее:
string fread(int $f, int $numbytes)
В параметрах функции задаются:
- $f – файл, заранее открытый через функцию fopen();
- $numbytes – количество символов, которые необходимо прочитать.
Функция возвращает блок символов в количество $numbytes. Если $numbytes
задан больше, чем общее количество символов в файле, то считывается весь
файл, а оставшаяся память впоследствии очищается «сборщиком мусора».
Функция поблочной записи в файл – fwrite():
int fwrite(int $f, string $st [, int $length])
Записывает в файл $f строку $st. Если задан необязательный параметр $length
– записывает только установленное им количество символов из строки $st.

Построчные чтение и запись


В случае необходимости построчного чтения файла существует функция
fgets(), осуществляющая чтение до первого символа окончания строки \n:
string fgets(int $f [, int $length])
Параметры функции:
- $f – файл, открытый для работы;
- $length – длина строки (если при чтении, количество символов меньше длины
строки и не достигает символа \n, то производится чтение только указанного
количества символов).
Функция записи
int fputs(int $f, string $st),
фактически, является синонимом функции fwrite().

Указатель конца файла


int feof(int $f)
Возвращает true, если достигнут конец файла $f. Подобная конструкция чаще
всего применяется в условном операторе if() при чтении из файла, хотя в
настоящий момент ее использование не рекомендуется в силу медлительности.

3
Лекции курса PHP7 +MySQL с нуля
(краткое содержание)

Положение указателя в файле


В случаях, когда указатель чтения/записи необходимо установить в
определенное место, используется функция fseek():
int fseek(int $f, int $offset [, int $where = SEEK_SET])
В параметрах этой функции задаются:
- $f – имя файла, в котором производится поиск;
- $offset – отступ от начальной позиции;
- $where – параметр, задающий начальную позицию смещения на параметр
$offset. Может принимать следующие значения:
- SEEK_SET – с начала файла, по умолчанию;
- SEEK_CUR – с текущей последней позиции;
- SEEK_END – с конца файла.
Примечательный момент – при использовании SEEK_END параметр $offset чаще
всего принимает отрицательные значения, иначе запись будет продолжаться за
концом файла и, соответственно, объем файла будет увеличен на добавляемый
объем записи.
Для поиска текущей позиции и сохранения ее в переменной Вы можете
воспользоваться функцией ftell():
int ftell(int $f)
Функция возвращает текущее положение указателя файла.

Обрезание файла
Для урезания файла до определенного объема при условии превышения его
допустимого объема, используется функция ftruncate():
bool ftruncate(int $f, int $newsize)
Файл $f обрезается до размера $newsize.
Настоятельно рекомендуется после функции ftruncate() использовать функцию
fseek() для перемещения указателя в существующее положение в новом размере
файла, иначе может произойти заполнение пустого пространства байтами при
последующем обращении к файлу.

Обработка файлов
Для обработки самих файлов предусмотрен ряд функций, среди которых
выделяются функции копирования, переименования и удаления файлов.
Рассмотрим каждую из них:
bool copy(string $src, string $dst)
Функция копирует файл $src в файл $dst. В случае, если файл $dst уже
существовал на момент запуска функции, происходит его полная перезапись.
bool rename(string $oldn, string $newn)
Функция производит переименование (или перемещение, что по сути является
одним и тем же) файла $oldn в файл $newn. Если файл $newn уже существует –
функция выдаст ошибку.
bool unlink(string $filename)
Функция производит удаление файла $filename. В случае неудачи возвращает
false. В случае с сетевым соединением производит разрыв соединения.
Все перечисленные функции содержат один необязательный параметр
$context, не указанный в данном разделе. Этот параметр определяет контекст
поддержки потоков, не рассматриваемых в данном курсе.

4
Лекции курса PHP7 +MySQL с нуля
(краткое содержание)

Чтение и запись файлов целиком


Для процедур чтения и записи в PHP определены еще несколько функций,
которые работают с файлами целиком. Рассмотрим их:
list file(string $filename [, int $flags, resource $context])
Читает файл $filename целиком, возвращая его в виде массива-списка, где
каждому элементу соответствует строка в файле. В качестве параметра $flags могут
быть использованы следующие константы:
- FILE_USE_INCLUDE_PATH – указывает осуществлять поиск в каталогах
библиотек PHP. Пути к таким каталогам содержатся в переменной
include_path файла настроек php.ini;
- FILE_IGNORE_NEW_LINES – указывает не добавлять символ новой строки
\n в конец каждого элемента массива;
- FILE_SKIP_EMPTY_LINES – указывает пропускать пустые строки.
Допускается указывать несколько параметров через знак побитового «или» - |.
Следующий способ получить содержимое файла – воспользоваться функцией
string file_get_contents(string $filename, bool $use_include_path = false, resource
$context, int $offset = -1, int $maxlength)
Данная функция считывает файл $filename целиком и возвращает
содержимое в виде строки.
Содержит следующие параметры:
- $use_include_path – равноценный константе FILE_USE_INCLUDE_PATH,
указывающей производить поиск среди каталогов библиотек PHP;
- $offset – смещение, относительно которого начнется чтение оригинального
потока. Не работает для сетевых соединений с файлами на удаленных
компьютерах.
- $maxlength – указывает максимальный размер читаемых данных, по
умолчанию установленный по размеру файла.
Для операции записи файла предусмотрена функция
int file_put_contents(string $filename, mixed $data [, int $flags = 0, resource $context])
Функция записывает данные $data в файл $filename. В случае, если файл не
существует, то функция создает этот файл. В случае существования такого файла,
происходит его перезапись или запись в конец файла при наличии в параметре
$flags константы FILE_APPEND.
Параметр $data может принимать различные типы, в т. ч. string и array.
Параметр $flags может содержать одну или несколько (через оператор |)
констант:
- FILE_USE_INCLUDE_PATH – уже рассмотренные ранее параметр поиска в
библиотеках PHP;
- FILE_APPEND – указывает на дозапись в конец файла, если файл с таким
именем уже существует;
- LOCK_EX – указывает на получение эксклюзивной блокировки файла на
время записи.

Практическая часть лекции по работе с файлами


Вынесение всех рассмотренных функций в одну общую часть сделано по
причине того, что в большинстве случаев работать Вы будете с файлами в
комплексе, но не с каждой функцией в отдельности. Таким образом, наиболее
логичным будет рассмотреть все функции в одном листинге, чем разбивать
примеры на множество по каждой функции.

5
Лекции курса PHP7 +MySQL с нуля
(краткое содержание)

Задача следующая – есть файл text.txt.


Необходимо проверить на нем действие различных способов чтения/записи,
предварительно сделав резервную копию этого файла.
Листинг 34.1. Работа с файлами

//Сделаем резервную копию файла путем копирования


copy('text.txt', 'text_rc.txt');

//ФУНКЦИИ fread() и fwrite()


//Открываем текстовый файл text.txt с параметром r+b
$file_source = fopen('text.txt', "r+b") or exit("Ошибка открытия файла!");

//Прочтем с помощью функции fread() первые 48 байт файла и выведем их на экран


$fread_str = fread($file_source, 46);
echo "<p><b>Результат работы функции fread():</b> {$fread_str}<p>";

//Изменим строку $fread_str, добавив текст "(или красный...)"


$fread_str .= " (или красный...)";

//Перезапишем файл text_fread_fwrite.txt новой строкой $fread_str


$frfw = fopen('text_fread_fwrite.txt', "c+b");
fwrite($frfw, $fread_str);

//Закрываем файлы
fclose($frfw);
fclose($file_source);
//-----------------------------------------------------

//ФУНКЦИИ fgets() и fputs()


//Открываем текстовый файл text.txt с параметром r+b
$file_source = fopen('text.txt', "r+b") or exit("Ошибка открытия файла!");

//Прочтем первую строку файла text.txt функцией fgets() и выведем ее на экран


$fgets_str = fgets($file_source);
echo "<p><b>Результат работы функции fgets():</b> {$fgets_str}<p>";

//Запишем эту строку в новый файл text_fg_fp.txt


$fgfp = fopen('text_fg_fp.txt', "c+b");
fputs($fgfp, $fgets_str);

//Закрываем файлы
fclose($fgfp);
fclose($file_source);
//-----------------------------------------------------

//ФУНКЦИИ file(), file_get_contents(), file_put_contents()

6
Лекции курса PHP7 +MySQL с нуля
(краткое содержание)

//Читаем данные файла функцией file() и выводим на экран


$file_arr = file('text.txt');
echo "<b>Текст из файла, прочитанный функцией file():</b>";
foreach($file_arr as $k => $v)
echo "<p>[{$k}] => $v</p>";

//Считываем последнюю строку функцией file_get_contents() и выводим на экран


$file_g_c = file_get_contents('text.txt', false, NULL, -45);
echo "<p><b>Строка из файла text.txt возвращенный функцией file_get_contents():</b>
{$file_g_c}</p>";

//Изменим текст строки с помощью функции замены в строке


$new_file_g_c = substr_replace($file_g_c, ', одиноко воя...', 17);

//Изменим последнюю строку, размещенную в виде массива-списка в переменной


$file_arr
$file_arr[3] = $new_file_g_c;

//Выведем массив-список с измененной последней строкой


echo "<b>Измененный текст из массива:</b>";
foreach($file_arr as $k => $v)
echo "<p>[{$k}] => $v</p>";

//Создадим и запишем файл с помощью функции file_put_contents()


file_put_contents('text_gc_pc.txt', $file_arr);

Результатом работы этого листинга будет:


1) Вывод на экране браузера:
Результат работы функции fread(): У лукоморья дуб зелёный
Результат работы функции fgets(): У лукоморья дуб зелёный;
Текст из файла, прочитанный функцией file():
[0] => У лукоморья дуб зелёный;
[1] => Златая цепь на дубе том:
[2] => И днём и ночью кот учёный
[3] => Всё ходит по цепи кругом;
Строка из файла text.txt возвращенный функцией file_get_contents(): Всё ходит по
цепи кругом;
Измененный текст из массива:
[0] => У лукоморья дуб зелёный;
[1] => Златая цепь на дубе том:
[2] => И днём и ночью кот учёный
[3] => Всё ходит, одиноко воя...
2) Новые файлы:
text_fg_fp.txt
text_fread_fwrite.txt
text_gc_pc.txt
text_rc.txt

7
Лекции курса PHP7 +MySQL с нуля
(краткое содержание)

Какие из функций выбирать для работы с файлами – индивидуальное дело


разработчика. Стоит лишь помнить, что каждая из них имеет свои особенности,
достоинства и недостатки.