Получение std :: ofstream и оператора перегрузки < - PullRequest
0 голосов
/ 05 июня 2018

Как получить из класса std :: ofstream, чтобы добавить несколько действий перед записью в файл?Другими словами, заменив код типа

int main()
{
   std::ofstream file("file.txt");
   file << "something" << std::endl;
   return 0;
}

на

class MyFile : public std::ofstream
{
   MyFile(std::string filename) : std::ofstream(filename) {}

   ??? operator<< ???   <-- HERE1
   {
      // 1. do some stuff with the input
      // 2. if wanted,
      // flush it to the base class operator<<
   }
};

class MyFileC
{
private:
   std::ofstream intern_os;
public:
   MyFileC(std::string filename) : intern_os(filename) {}

   MyFileC& operator<<( input ???   <-- HERE2  )
   {


          // 1. do some stuff with the input
          // e.g (a) IF the input is a std::string,
          // THEN, if it contains "signal",
          // OnSignal();
          // or (b) if file size is too big, clear it ...
          // 2. Flush it (for all possible types):

      intern_os << input;
   }
};

int main()
{
    MyFile file("file2.txt"); // (or with MyFileC)
    file << "something" << std::endl;
    return 0;
}

, где мы могли бы, например, фильтровать на лету перед записью и т. Д.

Что поставитьв ??? строках, чтобы насладиться всеми существующими std :: ofstream.operator << (), с нашими личными добавлениями, пожалуйста? </p>

  • ЗДЕСЬ1 : более элегантный, с наследственным подходом;или, если это невозможно (после комментариев ниже),
  • HERE2 : какой тип передать "всему, что может быть передано на внутренний std :: ofstream" (строки, целые, ...)

1 Ответ

0 голосов
/ 05 июня 2018

operator<< не предназначен для перезаписи производными потоковыми классами.Вместо этого вы должны переопределить std::basic_streambuf::overflow и / или std::basic_streambuf::xsputn.

overflow, в частности, вызывается внутренне всякий раз, когда буфер переполняется.Если вы хотите обеспечить свою собственную буферизацию, вы можете сделать это, инициализируя указатели потока с помощью std::basic_streambuf::setp внутри вашего переопределенного класса потока.Ссылки приводятся с примерами того, как это сделать.

Здесь есть только одна косметическая проблема: все это buffer методы.Вы хотите переопределить std::fstream, то есть класс stream , а не буфер класс .Поэтому вам нужно выполнить двойное действие:

  1. Переопределить std::basic_filebuf, как описано выше.
  2. Используйте std::fstream::rdbuf для установкисвязанный буфер объекта файлового потока с экземпляром вашего переопределенного класса файлового буфера.Вы можете сделать это либо на экземпляре существующего std::fstream, либо на пользовательском подклассе этого типа.
...