stl容器是否使用隐式共享?

Ash*_*hot 8 c++ stl

众所周知,Qt小部件使用隐式共享.所以我对stl容器感兴趣std::vector,也std::string使用隐式共享.

如果不是,为什么?因为它非常有用.

如果答案是肯定的,我们如何确定它?我需要简单的C++ stl程序,它表明stl容器使用隐式共享.复制时不执行深层复制.

ybu*_*ill 10

不,他们不能.当您尝试修改容器的内容,或者甚至begin()在其上调用mutable 时,它将意味着潜在的写入时复制,从而使容器的所有引用和迭代器无效.这将是一个难以调试的情况,并且是禁止的.

虽然std::string从技术上讲它不是一个容器,但是从C++ 11开始,它仍然被禁止进行copy-on-write:

引用basic_string序列元素的引用,指针和迭代器可能会被该basic_string对象的以下用法无效:
...
- 调用非const成员函数,除了operator [],at,front,back,begin, rbegin,end和rend.

[string.require]

...因为它非常有用.

嘿,为什么?通过引用传递几乎总能解决所有"性能问题".原子引用计数在多处理器机器上本质上是不可扩展的.

  • *它非常有用*评论需要放入Qt的内容 - 其设计者似乎厌恶有用的语言功能,例如异常和RTTI. (2认同)
  • @Marko:是的.Qt仍然是围绕90年代早期创建的同样狭隘的OO概念构建的......但是它今天是一个流行的GUI库这一事实并不表明它是一个很好的库,相反它只是说我们还没有更好的图书馆,或者这些图书馆没有赶上(不幸的是这就是好东西经常死的). (2认同)
  • +1.QtXML对于那些并不总是完全构造对象的构造函数,以及主要的习惯用法是每次检查错误标记都是最好的. (2认同)
  • @ybungalobill你是对的.我也愚蠢地说,Qt的实现并没有受到迭代器问题的影响.确实如此.哦,男孩 - 要解决这个问题,如果源上有活动的迭代器,就必须明确地`分离()`副本.叹.我必须审核[我所有答案中的代码](https://github.com/KubaO/stackoverflown),以确保我不会在任何情况下无意中暴露任何人. (2认同)

mar*_*rko 5

除了其他人对容器中的 CoW 行为提出的反对意见之外,还有以下一些反对意见。这些都属于违反惯例的行为类别,因此会导致毫无戒心的开发人员出现奇怪的错误。

例外情况

允许 CoW 意味着容器上无害的突变操作可能会失败,但会出现异常,否则它们不会失败。这对于operator[]astd::vectorstd::string

螺纹加工

人们可能合理地期望能够复制构造一个容器,其明确的目的是将其传递给另一个线程,而不必担心此后的并发性。CoW 则不然。