这应该是非常常见但我觉得很有意思,我找不到任何直接的解决方案。
基本上我通过网络将文件读入字符串流。这是宣言:
std::stringstream membuf(std::ios::in | std::ios::out | std::ios::binary);
现在我有一些C库需要直接访问内存的读取块。我怎么做到的?只读访问权限就可以了。 C函数完成后,我处理了内存流,不需要它。
str()
复制缓冲区,这似乎是不必要的,并使内存加倍。
我错过了一些明显的东西吗?也许一个不同的stl类可以更好地工作。
修改: 显然,stringstream不能保证连续存储。是什么?
如果我使用vector<char>
我如何获得字节缓冲区?
答案 0 :(得分:14)
您可以自己编写缓冲区并使用stringstream
stringstream membuf(std::ios::in | std::ios::out | std::ios::binary);
membuf.rdbuf(yourVeryOwnStreamBuf);
您自己的缓冲区应该来自basic_streambuf
,并适当地覆盖sync()
和overflow()
方法。
对于您的内部表示,您可以使用vector< char >
和reserve()
之类的内容来表达所需的大小,以便不会重新分配和复制。
这意味着您事先知道所需空间的上限。但如果你事先不知道大小,最后需要一个连续的缓冲区,副本当然是不可避免的。
答案 1 :(得分:11)
std::stringstream
不一定(必然)连续存储其缓冲区,但可以在逐渐填充时分配块。如果您希望将所有数据放在连续的内存区域中,那么您将需要复制它,这就是str()
为您所做的事情。
当然,如果您想使用或编写具有不同存储策略的类,则可以,但您根本不需要使用std::stringstream
。
答案 2 :(得分:8)
您可以调用str()
来获取std :: string。从那里你可以在std :: string上调用c_str()
来获得char*
。请注意,c_str()在此用途中不受官方支持,但每个人都以这种方式使用它:)
修改强>
这可能是一个更好的解决方案:std::istream::read
。从该页面上的示例:
buffer = new char [length];
// read data as a block:
is.read (buffer,length);
答案 3 :(得分:6)
好吧,如果你真的担心存储,你可以更接近金属。 basic_stringstream 有一个方法 rdbuf(),它返回 basic_stringbuf (它来自 basic_streambuf )。然后,您可以使用 eback(), egptr()和 gptr()指针直接从缓冲区中访问字符。我过去曾使用过这个机器来实现一个带有我想要的语义的自定义缓冲区,所以它是可行的。
小心,这不适合胆小的人!留出几天,阅读Standard C++ IOStreams and Locales或类似的挑剔参考,并小心......