How do I perform string formatting to a static buffer in C++?

牧云@^-^@ 提交于 2021-01-28 07:59:41

问题


I am working in a section of code with very high performance requirements. I need to perform some formatted string operations, but I am trying to avoid memory allocations, even internal library ones.

In the past, I would have done something similar to the following (assuming C++11):

constexpr int BUFFER_SIZE = 200;
char buffer[BUFFER_SIZE];
int index = 0;
index += snprintf(&buffer[index], BUFFER_SIZE-index, "Part A: %d\n", intA);
index += snprintf(&buffer[index], BUFFER_SIZE-index, "Part B: %d\n", intB);
// etc.

I would prefer to use all C++ methods, such as ostringstream, to do this instead of the old C functions.

I realize I could use std::string::reserve and std::ostringstream to procure space ahead of time, but that will still perform at least one allocation.

Does anyone have any suggestions?

Thanks ahead of time.


回答1:


Does anyone have any suggestions?

Yes, use std::ostrstream. I know it is deprecated. But I find it useful for output to static buffers. No possibility of memory leaks if an exception occurs. No allocation of memory at all.

#include <strstream> // for std::ostrstream
#include <ostream>   // for std::ends
// :

constexpr int BUFFER_SIZE = 200;
char buffer[BUFFER_SIZE];
std::ostrstream   osout(buffer, sizeof(buffer));
osout << "Part A: " << intA << "Part B: " << intB << std::ends;



回答2:


My thanks to all that posted suggestions (even in the comments).

I appreciate the suggestion by SJHowe, being the briefest solution to the problem, but one of the things I am looking to do with this attempt is to start coding for the C++ of the future, and not use anything deprecated.

The solution I decided to go with stems from the comment by Remy Lebeau:

#include <iostream>  // For std::ostream and std::streambuf
#include <cstring>   // For std::memset

template <int bufferSize>
class FixedBuffer : public std::streambuf
{
public:
   FixedBuffer()
      : std::streambuf()
   {
      std::memset(buffer, 0, sizeof(buffer));
      setp(buffer, &buffer[bufferSize-1]);         // Remember the -1 to preserve the terminator.
      setg(buffer, buffer, &buffer[bufferSize-1]); // Technically not necessary for an std::ostream.
   }

   std::string get() const
   {
      return buffer;
   }

private:
   char buffer[bufferSize];
};

//...

constexpr int BUFFER_SIZE = 200;
FixedBuffer<BUFFER_SIZE> buffer;
std::ostream ostr(&buffer);

ostr << "PartA: " << intA << std::endl << "PartB: " << intB << std::endl << std::ends;


来源:https://stackoverflow.com/questions/51162346/how-do-i-perform-string-formatting-to-a-static-buffer-in-c

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!