Стивен Прата - Язык Си - руководство для начинающих стр 35.

Шрифт
Фон

Третий параметр является указателем на файл; это значение возвращается функцией:

FILE *in;

in = fopen("test", "r");

Теперь in является указателем на файл "test". С этого момента программа ссылается на файл при помощи указателя in, а не по имени test.

Если вы очень сообразительны, то теперь можете задать такой вопрос: "Если fopen( ) возвращает указатель на 'FILE' в качестве аргумента, то почему мы не должны объявить fopen( ) как функцию указателя на 'FILE' ?" Хороший вопрос. Ответ заключается в том, что это описание сделал для нас файл stdio.h, который содержит строку

FILE *topen( );

Есть еще один важный момент относительно функции fopen(), которую мы использовали. Если fopen() не способна открыть требуемый файл, она возвращает значение 'NULL' (определенное в stdio.h как 0). Почему она не смогла открыть файл? Вы можете попросить ее считать файл, который не существует. Вот почему мы имеем в программе строку

if((in=fopen("test", "r"))!= NULL)

Заполнение диска, использование запрещенного имени или некоторые другие причины могут препятствовать открытию файла. Поэтому побеспокойтесь, чтобы их не было - маленькая ошибка может увести вас очень далеко.

Закрыть файл проще.

Закрытие файла: fclose( )

fclose(in);

Просто используйте функцию fclose( ). Заметим, что аргументом ее является in, указатель на файл, а не test, имя файла.

Для программы, более серьезной, чем эта, следовало бы посмотреть, успешно ли закрыт файл. Функция fclose( ) возвращает значение 0, если файл закрыт успешно, и -1 в противном случае.

Текстовые файлы с буферизацией

fopen()fclose()fclose( )

Текстовым считается файл, в котором информация запоминается в виде символов в коде ASCII (или аналогичном). Он отличается от двоичного файла, который обычно используется для запоминания кодов машинного языка. Функции ввода-вывода, о которых мы собираемся рассказать, предназначены только для работы с текстовыми файлами.

Ввод-вывод файла: getc( ) и putc( )

getc( )putc( )getchar( )putchar( )

ch = getchar( );

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

ch = getc(in);

- для получения символа от файла, на который указывает in. Аналогично функция

putc(ch, out);

предназначена для записи символа ch в файл, на который ссылается указатель out типа FILE. В списке аргументов функции putc( ) этот символ стоит первым, а затем указатель файла. В нашем примере мы использовали

putc(ch, stdout);

где stdout является указателем на стандартный вывод. Таким образом, этот оператор эквивалентен

putchar(ch);

Действительно, оператор putchar(ch) определен директивой #define так же как функция putc(ch, stdout) определена в файле stdio.h. Этот ужасный файл к тому же определяет в директиве #define указатели stdout

и stdin на стандартный вывод и стандартный ввод системы.

Это выглядит довольно просто? Хорошо, добавим пару полезных новшеств.

ПРОСТАЯ ПРОГРАММА СЖАТИЯ ФАЙЛА

/* сожмите ваши файлы в 2-3 раза! */

#include

main(argc, argv)

int argc;

char *argv[ ];

{

FILE *in, *out; /* описывает два указателя типа FILE */

int ch;

static char name[20]; /* память для имени выходного файла */

int count = 0;

if(argc < 2) /* проверяет, есть ли входной файл */

printf(" Извините, мне нужно имя файла в качестве аргумента.\n" );

else

{ if((in = fopen(argv[1], "r")) != NULL)

{

strcpy(name, argv[1]; /* копирует имя файла в массив */

strcat(name, ".red"); /* добавляет .red к имени */

out = fopen(name, "w"); /* открывает файл для записи */

while((ch = getc(in)) ! = EOF)

if( count ++ %3 ==0)

putc(ch, out); /* печатает каждый третий символ */

fclose(in);

fclosе(out); }

else

printf(" Я не смогла открыть файл\" %s\" .\n", argv[1]);

} }

РИС. 15.1. Программа сжатия файла.

Мы поместили программу в файл, названный reduce и применили эту программу к файлу, названному eddy, который содержал одну единственную строку

Даже Эдди нас опередил с детским хором.

Была выполнена команда

reduce eddy

и на выходе получен файл, названный eddy.red, который содержит

Дед спел тихо

Какая удача! Наш случайно выбранный файл сделал осмысленное сокращение.

Вот некоторые замечания по программе.

Вспомните, что argc содержит определенное количество аргументов, в число которых входит имя программного файла. Вспомните также, что с согласия операционной системы argv[0] представляет имя программы, т. е. в нашем случае reduce. Вспомните еще, что argv[l] представляет первый аргумент, в нашем случае eddy. Так как сам argv[l] является указателем на строку, он не должен заключаться в двойные кавычки в операторе вызова функции.

Мы используем argc, чтобы посмотреть, есть ли аргумент. Любые избыточные аргументы игнорируются. Помещая в программу еще один цикл, вы могли бы использовать дополнительные аргументы - имена файлов и пропускать в цикле каждый из этих файлов по очереди.

С целью создания нового имени выходного файла мы используем функцию strcpy( ) для копирования имени eddy в массив nаmе. Затем применяем функцию strcat( ) для объединения этого имени с .red.

Программа требует, чтобы два файла были открыты одновременно, поэтому мы описали два указателя типа 'FILE '. Заметим, что каждый файл должен открываться и закрываться независимо от другого. Существует ограничение на количество файлов, которые вы можете держать открытыми одновременно. Оно зависит от типа системы, но чаще всего находится в пределах от 10 до 20. Можно использовать один и тот же указатель для различных файлов при условии, что они нс открываются в одно и то же время.

Ваша оценка очень важна

0
Шрифт
Фон

Помогите Вашим друзьям узнать о библиотеке