用于C ++的可调整大小的char缓冲容器类型

时间:2011-08-23 05:57:47

标签: c++ data-structures stl

我正在使用带有C ++的libcurl(HTTP传输库)并尝试从远程HTTP服务器下载文件。下载文件时,多次调用我的回调函数(例如每10 kb)向我发送缓冲区数据。

基本上我需要类似“字符串缓冲”的东西,这是一种将char缓冲区附加到现有字符串的数据结构。在C中,我分配(malloc)一个char*然后作为新的缓冲区,我realloc然后memcpy,以便我可以轻松地将我的缓冲区复制到调整大小的数组。

在C中,有多种解决方案可以实现这一目标。

  1. 我可以继续使用mallocreallocmemcpy,但我很确定它们不会在C ++中使用。
  2. 我可以使用vector<char>
  3. 我可以使用stringstream
  4. 我的用例是,我会一次附加几千个项目(char s),在完成所有项目(下载完成)后,我会立即阅读所有项目。但是我将来可能需要像seek这样的选项(在阵列解决方案(1)中很容易实现),但现在它的优先级很低。

    我应该使用什么?

6 个答案:

答案 0 :(得分:1)

我会去stringstream。只需在收到数据时插入即可,当您完成后,您可以从中提取完整的std::string。我不明白你为什么要seek进入数组?无论如何,如果您知道块大小,则可以计算相应块的字符串中的位置。

答案 1 :(得分:1)

我不确定是否有人会同意这一点,但对于该用例,我实际上会使用链表,每个节点包含使用new分配的任意大的char数组。我的理由是:

  • 每次都以大块的形式添加项目,后面一次添加一个。
  • 我认为这可能会占用相当大的空间,因此当向量需要更多空间时,您可以避免重新分配事件。
  • 由于项目是按顺序读取的,因此单向链接列表的惩罚不会影响您。

如果通过列表寻求成为优先事项,这不会起作用。如果最终不是很多数据,我老实说认为矢量会很好,而不是 最有效的结构。

答案 2 :(得分:1)

如果您只需要附加char缓冲区,您也可以使用std::string和成员函数append。最重要的是stringstream为您提供了格式,功能,因此您可以添加数字,填充等,但是根据您的说明,您似乎不需要。

答案 3 :(得分:1)

我想我会使用deque<char>。与vector相同的接口,矢量可以做,但是每次附加超出其现有容量时,矢量需要复制整个数据。增长是指数级的,但您仍然期望重新分配log N,其中N是您追加的相等大小的数据块的数量。 Deque不会重新分配,因此在向量需要多次重新分配的情况下,它是首选容器。

假设回调被传递了char*缓冲区和长度,那么复制和附加数据的代码就足够简单了:

mydeque.insert(mydeque.end(), buf, buf + len);

如果你想要一个字符串,最后得到一个字符串:

std::string mystring(mydeque.begin(), mydeque.end());

我不完全确定seek的含义,但显然deque可以通过索引或迭代器访问,与vector相同。

另一种可能性是,如果您希望在下载开始时使用内容长度,则可以在启动之前使用vectorreserve()足够的空间来存储数据,从而避免再分配。这取决于您正在进行的HTTP请求以及哪些服务器,因为一些HTTP响应将使用分块编码,并且不会预先提供大小。

答案 4 :(得分:0)

我会使用vector<char>。但是他们的所有工作都会有所帮助,所以你的问题确实是风格问题,而且那里没有明确的答案。

答案 5 :(得分:0)

创建您自己的Buffer类以抽象出存储的详细信息。如果我是你,我可能会基于std::vector<char>实现缓冲区。