- 1、原创力文档(book118)网站文档一经付费(服务费),不意味着购买了该文档的版权,仅供个人/单位学习、研究之用,不得用于商业用途,未经授权,严禁复制、发行、汇编、翻译或者网络传播等,侵权必究。。
- 2、本站所有内容均由合作方或网友上传,本站不对文档的完整性、权威性及其观点立场正确性做任何保证或承诺!文档内容仅供研究参考,付费前请自行鉴别。如您付费,意味着您自己接受本站规则且自行承担风险,本站不退款、不进行额外附加服务;查看《如何避免下载的几个坑》。如果您已付费下载过本站文档,您可以点击 这里二次下载。
- 3、如文档侵犯商业秘密、侵犯著作权、侵犯人身权等,请点击“版权申诉”(推荐),也可以打举报电话:400-050-0827(电话支持时间:9:00-18:30)。
- 4、该文档为VIP文档,如果想要下载,成为VIP会员后,下载免费。
- 5、成为VIP后,下载本文档将扣除1次下载权益。下载后,不支持退款、换文档。如有疑问请联系我们。
- 6、成为VIP后,您将拥有八大权益,权益包括:VIP文档下载权益、阅读免打扰、文档格式转换、高级专利检索、专属身份标志、高级客服、多端互通、版权登记。
- 7、VIP文档为合作方或网友上传,每下载1次, 网站将根据用户上传文档的质量评分、类型等,对文档贡献者给予高额补贴、流量扶持。如果你也想贡献VIP文档。上传文档
查看更多
C 箴言:将new出来的对象存入智能指针
C++箴言:将new 出来的对象存入智能指针
不要忘记使用对象管理资源的至理名言,processWidget 为处理动态分配的 Widget 使用了
一个智能指针。
假设我们有一个函数取得我们的处理优先级,而第二个函数根据优先级针对动态分配的
Widget 做一些处理:
int priority();
void processWidget(std::tr1::shared_ptrWidget pw, int
priority);
不要忘记使用对象管理资源的至理名言,processWidget 为处理动态分配的 Widget 使
用了一个智能指针(在此,是一个 tr1::shared_ptr)。
现在考虑一个对 processWidget 的调用:
processWidget(new Widget,
priority());
且慢,别想这样调用。它不能编译。tr1::shared_ptr 的构造函数取得一个裸指针(raw
pointer)应该是显式的,所以不能从一个由 new Widget 返回的裸指针隐式转型到
processWidget 所需要的 tr1::shared_ptr.下面的代码,无论如何,是可以编译的:
processWidget(std::tr1::shared_ptrWidget(new Widget),
priority());
令人惊讶的是,尽管我们在这里各处都使用了对象管理资源,这个调用还是可能泄漏资
源。下面就来说明这是如何发生的。
在编译器能生成一个对 processWidget 的调用之前,它们必须传递实际参数来计算形
式参数的值。第二个实际参数不过是对函数 priority 的调用,但是第一个实际参数
(std::tr1::shared_ptrWidget(new Widget)),由两部分组成:
·表达式 new Widget 的执行。
·一个对 tr1::shared_ptr 的构造函数的调用。
在 processWidget 能被调用之前,编译器必须为这三件事情生成代码:
·调用 priority。
·执行 new Widget。
·调用 tr1::shared_ptr 的构造函数。
C++ 编译器允许在一个相当大的范围内决定这三件事被完成的顺序。(这里与 Java 和
C# 等语言的处理方式不同,那些语言里函数参数总是按照一个精确的顺序被计算。)new
Widget 表达式一定在 tr1::shared_ptr 的构造函数能被调用之前执行,因为这个表达式
的结果要作为一个参数传递给 tr1::shared_ptr 的构造函数,但是 priority 的调用可以
被第一个,第二个或第三个执行。如果编译器选择第二个执行它(大概这样能使它们生成更
有效率的代码),我们最终得到这样一个操作顺序:
·执行 new Widget。
·调用 priority。
·调用 tr1::shared_ptr 的构造函数。
但是请考虑,如果对 priority 的调用引发一个异常将发生什么。在这种情况下,从
new Widget 返回的指针被丢失,因为它没有被存入我们期望能阻止资源泄漏的
tr1::shared_ptr。由于一个异常可能插入资源创建的时间和将资源交给一个资源管理对象
的时间之间,所以调用 processWidget 可能会发生一次泄漏。避免类似问题的方法很简单:
用一个单独的语句创建 Widget 并将它存入一个智能指针,然后将这个智能指针传递给
processWidget:
std::tr1::shared_ptrWidget pw(new Widget); // store newed
object
// in a smart pointerin a
// standalonestatement
processWidget(pw,priority()); // thiscallwon’t leak
这样做是因为编译器在不同的语句之间重新安排操作顺序的活动余地比在一个语句之
内要小得多。new Widget 表达式和 tr1::shared_ptr
您可能关注的文档
最近下载
- 2025【基于哈佛分析框架的企业财务分析国内外文献综述3100字】.docx VIP
- 人工智能技术在企业管理决策中的应用与发展研究.docx VIP
- 全球玉米供需形势分析及后市价格展望(1).pptx VIP
- 护渔员考试题目及答案.doc VIP
- 压缩空气储能地下储气库工程施工方案.docx VIP
- SAJ三晶PDG10智能水泵变频器用户手册使用说明书.pdf
- 西南大学教学示范楼暖通设计.docx
- 武汉大学《环境微生物学》内部题库练习期末真题汇编及答案.docx
- 华南理工大学《数据库系统》15-17年历年期末考试试卷(部分含答案).pdf VIP
- CECA_GC 4-2017_建设项目全过程造价咨询规程.pdf
原创力文档


文档评论(0)