Одна из основных целей использования потоков состоит в инкапсуляции процедуры обмена данными с диском или дисплеем компьютера. Сама программа работает только с потоками, которые реализуют эти процессы. Схематически эта идея проиллюстрирована на рис. 16.1.
Рис. 16.1. Инкапсуляция с помощью потоков
Запись на диск (и в меньшей степени вывод на экран) обходится очень дорого. Запись данных на диск и считывание их с диска требует довольно много времени, что может надолго заблокировать выполнение программы. Для решения этой проблемы потоки обеспечивают буферизацию. Данные сначала записываются в буфер потока, а после его наполнения вся информация разом записывается на диск.
Суть идеи проиллюстрирована на примере знакомого со школьной скамьи бака с в.одой (рис. 16.2). Вода заливается сверху, и бак постепенно наполняется, поскольку нижний вентиль закрыт.
Когда вода (данные) достигает верха, нижний вентиль автоматически открывается и вся вода выливается (рис. 16.3).
Как только бак опустеет, нижний вентиль закрывается, а верхний открывается вновь, и вода снова поступает в бак (рис. 16.4).
В некоторых случаях необходимо, чтобы вода сразу же выливалась из бака, не дожидаясь его наполнения. В программировании такая ситуация называется очисткой буфера (рис. 16.5).
Рис. 16.2. Буфер наполняется данными, как закрытый бак — водой
Рис. 16.3. Открывается сливной вентиль, и вода (данные) сливается из бака
Рис. 16.4. Повторное наполнение бака
Рис. 16.5. Очистка буфера подобна экстренному сливу воды
В C++ применяется объектно-ориентированный подход к реализации обмена данными с буферизированными потоками.
• Класс streambuf управляет буфером, поэтому его функции предоставляют возможность наполнять, опорожнять и очищать буфер, а также выполнять с ним другие операции.
• Класс ios является базовым для классов потоков ввода-вывода. В качестве переменной-члена класса ios выступает объект streambuf.
• Классы istream и ostream являются производными от класса ios и отвечают соответственно за потоковый ввод и вывод данных.
• Класс iosteam является производным от классов istream и ostream и обеспечивает методы ввода-вывода для печати на экран.
• Классы fstream используются для ввода-вывода из файлов.
Стандартные объекты ввода-вывода
При запуске программы, включающей классы iostreams, создаются и инициируются четыре объекта.
Примечание: Библиотека класса iostream встроена в компилятор. Чтобы добавить в свою программу методы этого класса, достаточно в первых строках программы включить выражение #include.
• Объект cin (произносится как "си-ин" от английского "see-in") обрабатывает ввод с клавиатуры.
• Объект cout (произносится как "си-аут" от английского "see-out") обрабатывает вывод на экран.
• Объект cerr (произносится как "си-эр" от английского "see-err") обрабатывает не буферизированный вывод ошибок на стандартное устройство вывода сообщений об ошибках, т.е. на экран. Поскольку вывод не буферизированный, то все данные, направляемые в c err, сразу же выводятся устройством вывода.
• Объект clog (произносится как "си-лог" от английского "see-log") обрабатывает буферизированные сообщения об ошибках, которые выводятся на стандартное устройство вывода сообщений об ошибках (экран). Зачастую эти сообщения переадресуются в файл регистрации. Об этом вы узнаете далее в главе.
Каждое стандартное устройство ввода и вывода, в том числе устройство вывода сообщений об ошибках, может осуществлять переадресацию на другие устройства. Например, системные сообщения об ошибках часто переадресуются в файл регистрации. Для ввода и вывода данных программой также можно использовать файлы, для чего служат специальные команды операционной системы.
Под переадресацией понимают пересылку выводимых данных в устройство, либо считывание данных с устройства, отличное от установленного по умолчанию. В операционных системах DOS и UNIX используются специальные операторы переадресации ввода (<) и вывода (>).
Читать дальше