为什么gcc-4.9.2不能支持std :: string.insert(iterator,range)来返回迭代器

pez*_*ezy 6 c++ c++11 gcc4.9

根据cppreference,C++ 11应该支持:

template< class InputIt >
iterator insert( const_iterator pos, InputIt first, InputIt last );
Run Code Online (Sandbox Code Playgroud)

但是当我尝试使用g ++ 4.9.2编译以下代码时:

std::string str{ "hello world" }, addition{ "h my" };
auto iter = str.erase(str.begin(), str.begin() + 4);
iter = str.insert(next(iter), addition.begin(), addition.end()); // Error
Run Code Online (Sandbox Code Playgroud)

我收到以下错误(实例):

error: no match for 'operator=' (operand types are '__gnu_cxx::__normal_iterator<char*, std::basic_string<char> >' and 'void')
 iter = str.insert(next(iter), addition.begin(), addition.end());
      ^
Run Code Online (Sandbox Code Playgroud)

但是,Visual Studio 2013和Clang似乎没问题.

Sha*_*our 3

gcc 使用了不合格的写时复制(COW)实现,4.9.2他们连续改变了这一点5.x,我们可以从实时的 godbolt 会话中看到,这4.9.25.1.

此更改记录在GCC 5 发行系列发行说明中:

默认情况下启用 std::string 的新实现,使用小字符串优化而不是写入时复制引用计数。

我们可以从 [libstdc++ 邮件列表:新的 std::string 实现 ( https://gcc.gnu.org/ml/gcc-patches/2014-11/msg01785)中找到 COW 和 SSO 版本之间差异的描述。 html):

这是 std::string 期待已久的 ABI 突破,用符合 C++11 的 Small-String-Optimization 实现(基于 Paolo 的 vstring)取代了我们古老的 Copy-On-Write 实现。

它的要点是添加第二个完整的 std::string 实现,该实现用 abi_tag("cxx11") 标记,因此它的破坏方式不同(就像已经对 std::list 和 std::ios_base::failure 所做的那样)。