std::string 的 Copy-on-Write:不如想象.pdf

std::string 的 Copy-on-Write:不如想象.pdf

  1. 1、本文档共4页,可阅读全部内容。
  2. 2、原创力文档(book118)网站文档一经付费(服务费),不意味着购买了该文档的版权,仅供个人/单位学习、研究之用,不得用于商业用途,未经授权,严禁复制、发行、汇编、翻译或者网络传播等,侵权必究。
  3. 3、本站所有内容均由合作方或网友上传,本站不对文档的完整性、权威性及其观点立场正确性做任何保证或承诺!文档内容仅供研究参考,付费前请自行鉴别。如您付费,意味着您自己接受本站规则且自行承担风险,本站不退款、不进行额外附加服务;查看《如何避免下载的几个坑》。如果您已付费下载过本站文档,您可以点击 这里二次下载
  4. 4、如文档侵犯商业秘密、侵犯著作权、侵犯人身权等,请点击“版权申诉”(推荐),也可以打举报电话:400-050-0827(电话支持时间:9:00-18:30)。
查看更多
std::string 的 Copy-on-Write:不如想象

std ::string 的 Copy-on-Write:不如想象中美好 Copy-on-w rite (以下简称COW )是一种很重要的优化手段。它的核心思想是懒 处理多个实 体的资源请求,在多个实体之间共享某些资源,直到有实体需要对资源进行修改时,才真正为该 实体分配私有的资源。 COW技术的一个经典应用在于Linux 内核在进程fork时对进程地址空间的处理。由于fork产生 的子进程需要一份和父进程内容相同但完全独立的地址空间,一种做法是将父进程的地址空间完 全复制一份,另一种做法是将父进程地址空间中的页面标记为”共享的“ (引用计数+1),使子进程 与父进程共享地址空间,但当有一方需要对内存中某个页面进行修改时,重新分配一个新的页 面 (拷贝原内容),并使修改进程的虚拟地址重定向到新的页面上。 COW技术有哪些优点呢? 1. 一方面减少了分配 (和复制)大量资源带来的瞬间延迟 (注意仅仅是latency ,但实际上该 延迟被分摊到后续的操作中,其累积耗时很可能比一次统一处理的延迟要高,造成throughput下降 是有可能的) 2. 另一方面减少不必要的资源分配。 (例如在fork的例子中,并不是所有的页面都需要复制, 比如父进程的代码段 .code)和只读数据 .rodata)段,由于不允许修改,根本就无需复制。而如 果fork后面紧跟exec 的话,之前的地址空间都会废弃,花大力气的分配和复制只是徒劳无功。) COW 的思想在资源管理上被广泛使用,甚至连STL中的std ::string 的实现也要沾一下边。陈硕 的这篇博客 《C++工程实践 (10 ):再探std ::string》充分探讨了各个STL实现中对std ::string 的实 现方式,其中g++ std ::string和Apache stdcxx就使用了COW技术。 (其他对std ::string 的实现包 括eager copy和small string optimization,建议参考原博客,图文并茂十分清楚) 很简单一段代码,就能查看当前std ::string实现是否使用了COW : 如果实现使用了COW,那么第一个比较会返回true,第二个比较会返回false 。经测 试libstdc++ gcc 4.5)确实使用了COW,而查看STL中string 的源码,也确实采用了引用计数的手段 。 但要注意,std ::string 的lazy-copy行为只发生在两个string对象之间的拷贝构造,赋值 和assign )操作上,如果一个string 由const)char*构造而来,则必然会分配内存和进行复制,因 为string对象并不知道也无权控制char*所指内存的生命周期。 实际上,std ::string c = a.data )确实是一种在字符串赋值时禁止COW行为的方法。 看起来使用COW管理string来减少不必要的拷贝似乎很有效,然而在多数C++ STL实现中, 只有寥寥两种使用了COW,而同样著名的Visual C++ 2010)和clang libc++却不约而同抛弃 了COW,选择了SSO (small string optimization,足够小的字符串直接放在对象本身的栈内存中 ,避免了向Heap动态请求内存的开销)。 SSO对小字符串的高效是原因之一 (程序中通常会有大量的短字符串),而COW本身的缺陷 更是原因之一。 更多精彩攻略访问 1 更是原因之一。 一、性能:for thread-safety ! 想要实现COW,必须要有引用计数 (reference count )。string初始化时rc=1,每当该string 赋值给了其他sring,rc++。当需要对string做修改时,如果rc1,则重新申请空间并复制一份原字 符串的拷贝,rc– 。当rc减为0时,释放原内存。 基于”共享“和”引用“计数的COW在多线程环境下必然面临线程安全的问题。那么: std ::string是线程安全的吗? 在stackoverflow上对这个问题的一个很好的回答:是又不是。 从在多线程环境下对共享的string对象进行并发操作的角度来看,std ::string不是线程安全的, 也不可能是线程安全

文档评论(0)

yan698698 + 关注
实名认证
内容提供者

该用户很懒,什么也没介绍

1亿VIP精品文档

相关文档