Как мне создать свой собственный ostream / streambuf?

StackOverflow https://stackoverflow.com/questions/524641

  •  22-08-2019
  •  | 
  •  

Вопрос

В образовательных целях я хочу создать ostream и stream buffer для выполнения:

  1. исправьте конечные значения при выполнении << миВар;
  2. хранить в контейнере deque вместо использования std: cout или записи в файл
  3. регистрируйте дополнительные данные, например, сколько раз я делал <<, сколько раз я делал .write, количество байт, которые я записал, и сколько раз я сбрасывал ().Но мне не нужна вся информация.

Я попытался перегрузить, но потерпел ужасную неудачу.Я попытался перегрузить запись, выполнив

ostream& write( const char* s, streamsize n ) 

в моем классе basic_stringstream2 (я скопировал вставку basic_stringstream в мой cpp-файл и изменил его), но код продолжал использовать basic_ostream.Я просмотрел код, и похоже, что мне нужно перегрузить xsputn (что не упоминается на этой странице http://www.cplusplus.com/reference/iostream/ostream ) но что еще мне нужно для перегрузки?и как мне создать свой класс (что ему нужно унаследовать и т.д.)?

Это было полезно?

Решение

Канонический подход заключается в определении вашего собственного streambuf.Вам следует взглянуть на:

Другие советы

Для A + C) Я думаю, вам следует взглянуть на фасеты, они изменяют способ записи объектов в виде символов.Вы также можете хранить здесь статистику о том, сколько раз вы транслировали свои объекты в потоковом режиме.Проверьте Как отформатировать мои собственные объекты при использовании потоков STL? для примера.

Для B) Вам нужно создать свой собственный streambuf и подключить свой ostream к этому буферу (аргумент конструктора).Видишь Ссылки Люка + Получение новых классов streambuf.Короче говоря, вам нужно реализовать это для ostream (минимум):

  • переполнение (поместить один символ или очистить буфер) (Ссылка)
  • xsputn (поместить массив символов в буфер)(Ссылка)
  • синхронизация (Ссылка)

Я не уверен, что то, что вы хотите сделать, возможно.В << операторы не являются виртуальными.Таким образом, вы могли бы определить yourstream &operator << (yourstream &strm, int i) делать то, что вы хотите, с преобразованием в конце и подсчетом, и это будет работать, когда ваш код вызовет это напрямую.Но если вы передаете объект yourstream в функцию, которая ожидает ostream, каждый раз, когда эта функция вызывает <<, он перейдет к оригинальной версии ostream вместо вашей.

Насколько я понимаю, средства streams были настроены так, что вы можете "легко" определить новый тип потока, который использует другой тип буфера (например, набор символов), и вы можете очень легко добавить поддержку вывода ваших собственных классов через <<.Я не думаю, что вы предназначены для того, чтобы иметь возможность переопределить средний слой между ними.

И, в частности, весь смысл << интерфейс предназначен для обеспечения вывода красиво отформатированного текста, в то время как это звучит так, как будто вы на самом деле хотите двоичный вывод.(В противном случае ссылка на "endian" не имеет смысла.) Даже если предположить, что есть какой-то способ сделать это, которого я не знаю, в лучшем случае это приведет к неудобному двоичному выводу.Например, рассмотрим перегрузку конечного пользователя для вывода точки в трехмерном пространстве.Версия для конечного пользователя << вероятно, сделает что-то вроде << '(' << x << ", " << y << ", " << z << ')'.Это будет хорошо смотреться в текстовом потоке, но в двоичном потоке это много потраченных впустую и совершенно бесполезных символов, которые в идеале просто использовали бы << x << y << z.(И сколько звонков в << должны ли они считаться как?)

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top