32 Ошибки потоков. Файловый ввод-вывод с применением потоков C++.
Каждый поток (istream илиostream) имеет связанное с ним состояние. Установкой и соответствующей проверкой этого состояния вылавливаются ошибки и нестандартные условия.
Состояние потока вводится в basic_ios, базовом классе класса basic_stream, в <ios>.
Таблица 8
Функция
Описание действия
bool good() const;
следующая операция может выполниться
bool fail() const;
следующая операция не выполнится
bool eof() const;
виден конец ввода
bool bad() const;
поток испорчен
iostate rdstate() const;
получение флагов состояния ввода/вывода
void clear(iostate f=goodbit);
сбрасываются флаги ошибок (по умолчанию - все). Обычно после возникновения ошибки нужно сбросить ошибочное состояние, чтобы дальше пользоваться потоком, но этого недостаточно – для восстановления работоспособности еще нужно вручную очистить буфер ввода/вывода.
void setstate(iostate f) {clear(rdstate() | f);}
добавление f к флагам состояния
operator void*() const;
не ноль, если !fail()
bool operator!() const {return fail();}
не good()
Состояние потока представляется набором флагов. Эти флаги определены в базовом классе ios:
enum io_state
{
goodbit = 0x00. //Нет ошибок
eofbi t = 0x01, //Достигнут конец файла
failbit = 0x02, //Ошибка форматирования или преобразования
badbit = 0x04. //Серьезная ошибка, после которой
}; //пользоваться потоком невозможно.
Чтобы открыть для вывода файл myfile.txt с помощью объекта ofstream, необходимо создать экземпляр объекта класса ofstream и передать ему имя файла в качестве параметра: ofstream fout («myfile.txt»).
Чтобы открыть этот файл для ввода, применяется та же методика, за исключением того, что используется объект класса ifstream: ifstream fin («myfile.txt»).
Обратите внимание, что fout и fin не более чем имена объектов; здесь fout использовался для вывода в файл подобно тому, как cout используется для вывода на экран; fin аналогичен сin.
Очень важным методом, используемым в файловых потоках, является функция-член close(). Каждый раз при открытии файла для чтения или записи (или и того и другого) создается соответствующий объект файлового потока. По завершении работы файл необходимо закрыть (например: fout.close();), чтобы впоследствии не повредить его и записанные в нем данные. На практике нередко бывают непредвиденные случаи, когда не закрытые файлы теряют всю внесенную в них информацию.
После того как объекты потока будут ассоциированы с файлами, они используются наравне с другими объектами потока ввода и вывода. Например:
#include <fstream.h>
int main()
{ char buffer[255]; // для ввода пользователя
cout << “File name: “;
cin.getline (buffer,255);
ofstream fout(buffer); // открыть для записи
fout << “This line written directly to the file\n”;
cin.getline (buffer,255); // получить данные от пользователя
fout << buffer; // и запись их в файл
fout.close(); // закрыть файл
return 0; // уходя гасите свет
}
Обычно объект класса ofstream, открывая файл для записи, создает новый файл, если таковой не существует, или усекает его длину до нуля, если файл с этим именем уже существует (то есть удаляет все его содержимое). Изменить стандартное поведение объекта ofstream можно с помощью второго аргумента конструктора, заданного явно.
Допустимыми аргументами являются:
- ios::app — добавляет данные в конец файла, не усекая прежнее его содержимое;
- ios::ate — осуществляет переход в конец файла, но запись допускает в любом месте файла;
- ios::trunc — задано по умолчанию; усекает существующий файл полностью;