Керниган и Ритчи - Язык программирования Си (793773), страница 58
Текст из файла (страница 58)
идентификатор-> идентификатор++--первичное-выражение:идентификаторконстантастрока( выражение )список-аргументов-выражений:выражение-присваиваниясписок-аргументов-выражений , выражение-присваиванияконстанта:целая-константасимвольная-константаконстанта-с-плавающей-точкойконстанта-перечислениеНиже приводится грамматика языка препроцессора в виде перечня структур управляющих строк.
Длямеханического получения программы грамматического разбора она не годится. Грамматика включает символтекст, который означает текст обычной программы, безусловные управляющие строки препроцессора и егозаконченные условные конструкции.управляющая-строка:# define идентификатор последовательность-лексем# define идентификатор ( идентификатор ... идентификатор )последовательность-лексем# undef идентификатор# include <имя-файла># include "имя-файла"# include последовательность-лексем# line константа "идентификатор"# line константа# error последовательность-лексемнеоб# pragma последовательность-лексемнеоб#условная-конструкция-препроцессораусловная-конструкция-препроцессора:if-строка текст elif-части else-частьнеоб # endifif-строка:# if константное-выражение# ifdef идентификатор# ifndef идентификаторelif-части:elif-строка текстelif-частинеобelif-строка:# elif константное-выражениеelse-часть:else-строка текстеlsе-строка:# elseB.
Стандартная библиотекаНастоящее приложение представляет собой краткое изложение библиотеки, утвержденной в качестве ANSIстандарта. Сама по себе библиотека не является частью языка, однако заложенный в ней набор функций, атакже определений типов и макросов составляет системную среду, поддерживающую стандарт Си. Мы неприводим здесь несколько функций с ограниченной областью применения — те, которые легкосинтезируются из других функций, а также опускаем все то, что касается многобайтовых символов испецифики, обусловленной языком, национальными особенностями и культурой.Функции, типы и макросы объявляются в следующих стандартных заголовочных файлах:<assert.h> <float.h> <math.h><stdarg.h> <stdlib.h><ctype.h> <limits.h> <setjmp.h> <stddef.h> <string.h><errno.h> <locale.h> <signal.h> <stdio.h> <time.h>Доступ к заголовочному файлу осуществляется с помощью строки препроцессора#include <заголовочный-файл>Заголовочные файлы можно включать в любом порядке и сколько угодно раз.
Строка #include не должнабыть внутри внешнего объявления или определения и должна встретиться раньше, чем что-нибудь извключаемого заголовочного файла будет востребовано. В конкретной реализации заголовочный файл можети не быть исходным файлом.Внешние идентификаторы, начинающиеся со знака подчеркивания, а также все другие идентификаторы,начинающиеся с двух знаков подчеркивания или с подчеркивания и заглавной буквы, зарезервированы дляиспользования в библиотеке.В 1.
Ввод-вывод: <stdio.h>Определенные в <stdio.h> функции ввода-вывода, а также типы и макросы составляют приблизительноодну треть библиотеки.Поток — это источник или получатель данных; его можно связать с диском или с каким-то другим внешнимустройством. Библиотека поддерживает два вида потоков: текстовый и бинарный, хотя на некоторыхсистемах, в частности в UNIXe, они не различаются. Текстовый поток — это последовательность строк; каждаястрока имеет нуль или более символов и заканчивается символом '\n' .
Операционная среда можетпотребовать коррекции текстового потока (например перевода '\n' в символы возврат-каретки и переводстроки).Бинарный поток — это последовательность непреобразованных байтов, представляющих собой некоторыепромежуточные данные, которые обладают тем свойством, что если их записать, а затем прочесть той жесистемой ввода-вывода, то мы получим информацию, совпадающую с исходной.Поток соединяется с файлом или устройством посредством его открытия, указанная связь разрываетсяпутем закрытия потока. Открытие файла возвращает указатель на объект типа FILE, который содержит всюинформацию, необходимую для управления этим потоком.
Если не возникает двусмысленности, мы будемпользоваться терминами "файловый указатель" и "поток" как равнозначными.Когда программа начинает работу, уже открыты три потока: stdin, stdout и stderr.В 1.1. Операции над файламиНиже перечислены функции, оперирующие с файлами. Тип size_t — беззнаковый целочисленный тип,используемый для описания результата оператора sizeof.FILE *fopen(const char *filename, const char *mode)fopen открывает файл с заданным именем и возвращает поток или NULL, если попытка открытияоказалась неудачной. Режим mode допускает следующие значения:"r" — текстовый файл открывается для чтения (от read (англ.) — читать);"w" — текстовый файл создается для записи; старое содержимое (если оно было) выбрасывается (отwrite (англ.) — писать);"а" — текстовый файл открывается или создается для записи в конец файла (от append (англ.) —добавлять);"r+" — текстовый файл открывается для исправления (т.
е. для чтения и для записи);"w+" — текстовый файл создается для исправления; старое содержимое (если оно было)выбрасывается;"а+" — текстовый файл открывается или создается для исправления уже существующей информациии добавления новой в конец файла.Режим "исправления" позволяет читать и писать в один и тот же файл; при переходах от операцийчтения к операциям записи и обратно должны осуществляться обращения к fflush или к функциипозиционирования файла. Если указатель режима дополнить буквой b (например, "rb" или "w+b"),то это будет означать, что файл бинарный. Ограничение на длину имени файла задано константойFILENAME_MAX. Константа FOPEN_MAX ограничивает число одновременно открытых файлов.FILE *freopen(const char *filename, const char *mode, FILE *stream)freopen открывает файл с указанным режимом и связывает его с потоком stream.
Она возвращаетstream или, в случае ошибки, NULL. Обычно freopen используется для замены файлов, связанных сstdin, stdout или stderr, другими файлами.int fflush(FILE *stream)Применяемая к потоку вывода функция fflush производит дозапись всех оставшихся в буфере (ещене записанных) данных; для потока ввода эта функция не определена. Возвращает EOF в случаевозникшей при записи ошибки или нуль в противном случае. Обращение вида fflush(NULL)выполняет указанные операции для всех потоков вывода.int fclose(FILE *stream)fсlose производит дозапись еще не записанных буферизованных данных, сбрасывает несчитанныйбуферизованный ввод, освобождает все автоматически запрошенные буфера, после чего закрываетпоток.
Возвращает EOF в случае ошибки и нуль в противном случае.int remove(const char *filename)remove удаляет файл с указанным именем; последующая попытка открыть файл с этим именемвызовет ошибку. Возвращает ненулевое значение в случае неудачной попытки.int rename(const char *oldname, const char *newname)rename заменяет имя файла; возвращает ненулевое значение в случае, если попытка изменить имяоказалась неудачной.
Первый параметр задает старое имя, второй — новое.FILE *tmpfile(void)tmpfile создает временный файл с режимом доступа "wb+", который автоматически удаляется приего закрытии или обычном завершении программой своей работы. Эта функция возвращает потокили, если не смогла создать файл, NULL.char *tmpnam(char s[L_tmpnam])tmpnam(NULL) создает строку, не совпадающую ни с одним из имен существующих файлов, ивозвращает указатель на внутренний статический массив.tmpnam(s) запоминает строку в s и возвращает ее в качестве значения функции; длина s должнабыть не менее L_tmpnam. При каждом вызове tmpnam генерируется новое имя; при этомгарантируется не более ТМР_МАХ различных имен за один сеанс работы программы.
Заметим, чтоtmpnam создает имя, а не файл.int setvbuf(FILE «stream, char *buf, int mode, size_t size)setvbuf управляет буферизацией потока; к ней следует обращаться прежде, чем будет выполнятьсячтение, запись или какая-либо другая операция. mode со значением _IOFBF вызывает полнуюбуферизацию, с _IOLBF — "построчную" буферизацию текстового файла, a mode со значением_IONBF отменяет всякую буферизацию. Если параметр buf не есть NULL, то его значение —указатель на буфер, в противном случае под буфер будет запрашиваться память.
Параметр sizeзадает размер буфера. Функция setvbuf в случае ошибки выдает ненулевое значение.void setbuf(FILE *stream, char *buf)Если buf есть NULL, то для потока stream буферизация выключается. В противном случае вызовsetbuf приведет к тем же действиям, что и вызов (void) setvbuf (stream, buf, _IOFBF,BUFSIZ).В 1.2. Форматный выводФункции printf осуществляют вывод информации по формату.int fprintf(FILE *stream, const char *format, ...)fprintf преобразует и пишет вывод в поток stream под управлением format. Возвращаемоезначение — число записанных символов или, в случае ошибки, отрицательное значение.Форматная строка содержит два вида объектов: обычные символы, копируемые в выводной поток, испецификации преобразования, которые вызывают преобразование и печать остальных аргументов в томпорядке, как они перечислены.














