stringstream :: str copy lifetime

时间:2014-02-03 18:19:24

标签: c++ memory stringstream

许多C ++程序员在第一次使用stringstream时错过(读取:我)的事实是stringstream::str()返回的副本是临时的,这种情况一直持续到表达式的结尾。用于。但是,我不明白:

  1. 如何做到这一点。查看libstdc ++的sstream标题,我只看到正在制作并返回的副本。寿命如何受限制?
  2. 为什么这是理想的行为,特别是因为它是如此常见的问题。如果正在制作副本,为什么我不能取得它的所有权呢?
  3. 请注意,这不是stringstream, string, and char* conversion confusion的副本。这解释了行为和变通方法;我正在寻找机制和理论基础。

3 个答案:

答案 0 :(得分:2)

这不是stringstream的问题。这是c_str函数的问题 - 它返回指向char*的{​​{1}}表示的指针,但它仅在原始字符串的生命周期内存在。当您致电std::string时,实际发生以下情况:

char *str = ss.str().c_str()

string tmp = ss.str(); char *str = tmp.c_str(); tmp.~string (); // after that line the pointer `str` is no longer valid 是一个危险功能,仅出于兼容性和速度目的而提供,您应该避免使用它。

答案 1 :(得分:0)

stringstream::str()返回string。期。它是通过价值来实现的,所以你可以随心所欲地做任何事情(例如肯定取得所有权)。

答案 2 :(得分:0)

  

这是怎么做到的?查看libstdc ++的sstream标题,我只看到正在制作并返回的副本。寿命如何受限?

str()按值返回,这意味着它返回的对象在完整表达式的末尾被销毁。这只是临时工作的方式。

  

为什么这是理想的行为,特别是因为它是如此常见的问题。如果正在制作副本,为什么我不能取得它的所有权呢?

这是传统IOStreams的修正案。旧的已弃用的流类strstream具有str()方法,该方法返回指向其内部缓冲区的指针。为了防止指针失效,必须“冻结”流,这意味着缓冲区无法调整大小。

标准IOStreams将缓冲区的副本作为std::basic_string<charT>对象返回,以便不再需要冻结流。