﻿<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:trackback="http://madskills.com/public/xml/rss/module/trackback/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/"><channel><title>C++博客-愚公移山-文章分类-Effective C++(3E)读书笔记</title><link>http://www.cppblog.com/yugong/category/5652.html</link><description>死而后已</description><language>zh-cn</language><lastBuildDate>Sat, 24 May 2008 13:22:35 GMT</lastBuildDate><pubDate>Sat, 24 May 2008 13:22:35 GMT</pubDate><ttl>60</ttl><item><title>Effective C++读书笔记—3 资源管理(之3)</title><link>http://www.cppblog.com/yugong/articles/37527.html</link><dc:creator>Nathan.Yu</dc:creator><author>Nathan.Yu</author><pubDate>Thu, 29 Nov 2007 16:36:00 GMT</pubDate><guid>http://www.cppblog.com/yugong/articles/37527.html</guid><wfw:comment>http://www.cppblog.com/yugong/comments/37527.html</wfw:comment><comments>http://www.cppblog.com/yugong/articles/37527.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/yugong/comments/commentRss/37527.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/yugong/services/trackbacks/37527.html</trackback:ping><description><![CDATA[<h1 style="text-align: center;" align="center"><span lang="EN-US">Effective C++</span><span style="font-family: 宋体;">读书笔记</span></h1>
<p class="MsoNormal" style="margin-left: 210pt; text-indent: 21pt;"><em><span style="font-size: 14pt;" lang="EN-US">--By
Nathan.Yu 2007-11-29--<o:p></o:p></span></em></p>
<h2><span lang="EN-US">3 </span><span style="font-family: 黑体;">资源管理</span><span lang="EN-US">(</span><span style="font-family: 黑体;">之三</span><span lang="EN-US">)</span></h2>
<h3><span style="font-family: 宋体;">条款</span><span lang="EN-US">15</span><span style="font-family: 宋体;">：在资源管理类中提供对原始资源的访问（</span><span lang="EN-US">Provide access to
raw resources in resource-managing classes</span><span style="font-family: 宋体;">）</span></h3>
<p class="MsoNormal" style="text-indent: 21pt;"><span style="font-family: 宋体; color: red;">许多</span><span style="color: red;" lang="EN-US">APIs</span><span style="font-family: 宋体; color: red;">需要指涉指针。</span><span style="color: red;" lang="EN-US"><o:p></o:p></span></p>
<p class="MsoNormal" style="text-indent: 21pt;"><span lang="EN-US"><o:p>&nbsp;</o:p></span></p>
<p class="MsoNormal" style="text-indent: 21pt;"><span style="font-family: 宋体;">将</span><span lang="EN-US">RAII class</span><span style="font-family: 宋体;">对象转换为原始资源的方法：</span></p>
<p class="MsoNormal" style="margin-left: 39pt; text-indent: -18pt;"><!--[if !supportLists]--><span lang="EN-US"><span>1、<span style="font-family: &quot;Times New Roman&quot;; font-style: normal; font-variant: normal; font-weight: normal; font-size: 7pt; line-height: normal; font-size-adjust: none; font-stretch: normal;">&nbsp;
</span></span></span><!--[endif]--><strong><span style="font-size: 15pt; font-family: 宋体; color: blue;">显式转换</span></strong><span style="font-family: 宋体;">：</span></p>
<p class="MsoNormal" style="text-indent: 21pt;"><span lang="EN-US">tr1::shared_ptr</span><span style="font-family: 宋体;">和</span><span lang="EN-US">auto_ptr</span><span style="font-family: 宋体;">都提供一个</span><span lang="EN-US">get</span><span style="font-family: 宋体;">成员函数，用来执行显式转换。也就是返回智能指针内部的原始指针。</span></p>
<p class="MsoNormal" style="margin-left: 39pt; text-indent: -18pt;"><!--[if !supportLists]--><span lang="EN-US"><span>2、<span style="font-family: &quot;Times New Roman&quot;; font-style: normal; font-variant: normal; font-weight: normal; font-size: 7pt; line-height: normal; font-size-adjust: none; font-stretch: normal;">&nbsp;
</span></span></span><!--[endif]--><strong><span style="font-size: 15pt; font-family: 宋体; color: blue;">隐式转换</span></strong><span style="font-family: 宋体;">：</span></p>
<p class="MsoNormal" style="text-indent: 21pt;"><span style="font-family: 宋体;">①、</span><span style="font-family: 宋体; color: #339966;">重载指针取值操作符</span><span style="color: #339966;" lang="EN-US">(operator-&gt;</span><span style="font-family: 宋体; color: #339966;">和</span><span style="color: #339966;" lang="EN-US">operator*)</span><span style="font-family: 宋体;">。</span></p>
<p class="MsoNormal" style="text-indent: 21pt;"><span style="font-family: 宋体;">②</span><span style="font-family: 宋体;">、<span style="color: #339966;">提供一个隐式转换函数：</span></span><span style="color: #339966;" lang="EN-US">operator T() const{return x;}</span><span style="font-family: 宋体;">。但这个隐式转换会增加错误发生机会。</span></p>
<p class="MsoNormal" style="text-indent: 21pt;"><span style="font-family: 宋体;">是否该提供一个显式转换函数或隐式转换函数，主要取决于</span><span lang="EN-US">RAII class</span><span style="font-family: 宋体;">被设计执行的特定工作，以及它被使用的情况。通常</span><span lang="EN-US">get</span><span style="font-family: 宋体;">函数更好，因为它将&#8220;非故意转换&#8221;的可能性最小化了。然而有时候，隐式转换所带来的&#8220;自然用法&#8221;也会引发天平倾斜。</span></p>
<p class="MsoNormal" style="text-indent: 21pt;"><span style="color: #ff6600;" lang="EN-US">RAII classes</span><span style="font-family: 宋体; color: #ff6600;">并不是为了封装某物存在的，它们的存在是为了确保一个特殊行为——资源释放——会发生。</span><span style="color: #ff6600;" lang="EN-US"><o:p></o:p></span></p>
<p class="MsoNormal" style="text-indent: 21pt;"><span lang="EN-US"><o:p>&nbsp;</o:p></span></p>
<p class="MsoNormal" style="text-indent: 21pt;"><span style="font-family: 宋体; color: red;">请记住：</span><span style="color: red;" lang="EN-US"><o:p></o:p></span></p>
<p class="MsoNormal" style="margin-left: 18pt; text-indent: -18pt;"><!--[if !supportLists]--><strong><span style="font-size: 14pt; color: purple;" lang="EN-US"><span>1、<span style="font-family: &quot;Times New Roman&quot;; font-style: normal; font-variant: normal; font-weight: normal; font-size: 7pt; line-height: normal; font-size-adjust: none; font-stretch: normal;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span></span></span></strong><!--[endif]--><strong><span style="font-size: 14pt; color: purple;" lang="EN-US">APIs</span></strong><strong><span style="font-size: 14pt; font-family: 宋体; color: purple;">往往要求访问原始资源（</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US">raw resources</span></strong><strong><span style="font-size: 14pt; font-family: 宋体; color: purple;">），所以每一个</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US">RAII class</span></strong><strong><span style="font-size: 14pt; font-family: 宋体; color: purple;">应该提供一个&#8220;取得其所管资源&#8221;的方法。</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US"><o:p></o:p></span></strong></p>
<p class="MsoNormal" style="margin-left: 18pt; text-indent: -18pt;"><!--[if !supportLists]--><strong><span style="font-size: 14pt; color: purple;" lang="EN-US"><span>2、<span style="font-family: &quot;Times New Roman&quot;; font-style: normal; font-variant: normal; font-weight: normal; font-size: 7pt; line-height: normal; font-size-adjust: none; font-stretch: normal;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span></span></span></strong><!--[endif]--><strong><span style="font-size: 14pt; font-family: 宋体; color: purple;">对原始资源的访问可能经由显式转换或隐式转换。一般而言显式转换比较安全，但隐式转换对客户比较方便。</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US"><o:p></o:p></span></strong></p><img src ="http://www.cppblog.com/yugong/aggbug/37527.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/yugong/" target="_blank">Nathan.Yu</a> 2007-11-30 00:36 <a href="http://www.cppblog.com/yugong/articles/37527.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Effective C++读书笔记—3 资源管理(之2)</title><link>http://www.cppblog.com/yugong/articles/37475.html</link><dc:creator>Nathan.Yu</dc:creator><author>Nathan.Yu</author><pubDate>Wed, 28 Nov 2007 16:43:00 GMT</pubDate><guid>http://www.cppblog.com/yugong/articles/37475.html</guid><wfw:comment>http://www.cppblog.com/yugong/comments/37475.html</wfw:comment><comments>http://www.cppblog.com/yugong/articles/37475.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/yugong/comments/commentRss/37475.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/yugong/services/trackbacks/37475.html</trackback:ping><description><![CDATA[<h1 style="text-align: center;" align="center"><span lang="EN-US">Effective C++</span><span style="font-family: 宋体;">读书笔记</span></h1>
<p class="MsoNormal" style="margin-left: 210pt; text-indent: 21pt;"><em><span style="font-size: 14pt;" lang="EN-US">--By
Nathan.Yu 2007-11-28--<o:p></o:p></span></em></p>
<h2><span lang="EN-US">3 </span><span style="font-family: 黑体;">资源管理</span><span lang="EN-US">(</span><span style="font-family: 黑体;">之二</span><span lang="EN-US">)</span></h2>
<h3><span style="font-family: 宋体;">条款</span><span lang="EN-US">14</span><span style="font-family: 宋体;">：在资源管理类中小心</span><span lang="EN-US">copying</span><span style="font-family: 宋体;">行为（</span><span lang="EN-US">Think carefully about copying
behavior in resource-managing classes</span><span style="font-family: 宋体;">）</span></h3>
<p class="MsoNormal" style="text-indent: 21pt;"><span lang="EN-US"><span>&nbsp;</span></span><span style="font-family: 宋体;">&#8220;<span style="color: red;">当一个</span></span><span style="color: red;" lang="EN-US">RAII</span><span style="font-family: 宋体; color: red;">对象被复制时，会发生什么？</span><span style="font-family: 宋体;">&#8221;这是每个</span><span lang="EN-US">RAII class</span><span style="font-family: 宋体;">作者必须面对的一般化问题。有</span><span lang="EN-US">4</span><span style="font-family: 宋体;">中可能：</span></p>
<p class="MsoNormal" style="margin-left: 39pt; text-indent: -18pt;"><!--[if !supportLists]--><span lang="EN-US"><span>1、<span style="font-family: &quot;Times New Roman&quot;; font-style: normal; font-variant: normal; font-weight: normal; font-size: 7pt; line-height: normal; font-size-adjust: none; font-stretch: normal;">&nbsp;
</span></span></span><!--[endif]--><strong><span style="font-size: 15pt; font-family: 宋体; color: blue;">禁止复制。</span></strong><span style="font-family: 宋体;">（见条款</span><span lang="EN-US">6</span><span style="font-family: 宋体;">：</span>
<span lang="EN-US">Uncopyable</span><span style="font-family: 宋体;">类）</span></p>
<p class="MsoNormal" style="margin-left: 39pt; text-indent: -18pt;"><!--[if !supportLists]--><span lang="EN-US"><span>2、<span style="font-family: &quot;Times New Roman&quot;; font-style: normal; font-variant: normal; font-weight: normal; font-size: 7pt; line-height: normal; font-size-adjust: none; font-stretch: normal;">&nbsp;
</span></span></span><!--[endif]--><strong><span style="font-size: 15pt; font-family: 宋体; color: blue;">对底层资源祭出&#8220;引用计数&#8221;</span></strong><strong><span style="font-size: 15pt; color: blue;" lang="EN-US">(reference-count)</span></strong><span style="font-family: 宋体;">。通常只要内含一个</span><span lang="EN-US">tr1::shared_ptr</span><span style="font-family: 宋体;">成员变量，</span><span lang="EN-US">RAII class</span><span style="font-family: 宋体;">便可实现出</span><span lang="EN-US">referenct-counting copying</span><span style="font-family: 宋体;">行为。即将成员</span><span lang="EN-US">T*</span><span style="font-family: 宋体;">改为</span><span lang="EN-US">tr1::shared_ptr&lt;T&gt;</span><span style="font-family: 宋体;">。</span></p>
<p class="MsoNormal" style="text-indent: 21pt;"><span lang="EN-US">tr1::shared_ptr</span><span style="font-family: 宋体;">的缺省行为是&#8220;当引用次数为</span><span lang="EN-US">0</span><span style="font-family: 宋体;">时删除所指对象&#8221;。但</span><span lang="EN-US">tr1::shared_ptr</span><span style="font-family: 宋体;">允许指定&#8220;删除器&#8221;（</span><span lang="EN-US">deleter</span><span style="font-family: 宋体;">）——是一个函数或函数对象</span><span lang="EN-US">(function object)</span><span style="font-family: 宋体;">，当引用次数为</span><span lang="EN-US">0</span><span style="font-family: 宋体;">时被调用。&#8220;删除器&#8221;（</span><span lang="EN-US">deleter</span><span style="font-family: 宋体;">）作为</span><span lang="EN-US">tr1::shared_ptr</span><span style="font-family: 宋体;">构造函数的第二个参数传入。</span></p>
<p class="MsoNormal" style="margin-left: 39pt; text-indent: -18pt;"><!--[if !supportLists]--><span lang="EN-US"><span>3、<span style="font-family: &quot;Times New Roman&quot;; font-style: normal; font-variant: normal; font-weight: normal; font-size: 7pt; line-height: normal; font-size-adjust: none; font-stretch: normal;">&nbsp;
</span></span></span><!--[endif]--><strong><span style="font-size: 15pt; font-family: 宋体; color: blue;">复制底部资源</span></strong><span style="font-family: 宋体;">。——&#8220;深度拷贝&#8221;，比如字符串类，当复制发生时，不论指针或指针所指内存都要被复制。</span></p>
<p class="MsoNormal" style="margin-left: 39pt; text-indent: -18pt;"><!--[if !supportLists]--><span lang="EN-US"><span>4、<span style="font-family: &quot;Times New Roman&quot;; font-style: normal; font-variant: normal; font-weight: normal; font-size: 7pt; line-height: normal; font-size-adjust: none; font-stretch: normal;">&nbsp;
</span></span></span><!--[endif]--><strong><span style="font-size: 15pt; font-family: 宋体; color: blue;">转移底部资源的拥有权</span></strong><span style="font-family: 宋体;">。如</span><span lang="EN-US">auto_ptr</span><span style="font-family: 宋体;">。</span></p>
<p class="MsoNormal" style="margin-left: 21pt;"><span lang="EN-US"><o:p>&nbsp;</o:p></span></p>
<p class="MsoNormal"><span style="font-family: 宋体; color: red;">请记住</span><span style="font-family: 宋体;">：</span></p>
<p class="MsoNormal" style="margin-left: 18pt; text-indent: -18pt;"><!--[if !supportLists]--><strong><span style="font-size: 14pt; color: purple;" lang="EN-US"><span>1、<span style="font-family: &quot;Times New Roman&quot;; font-style: normal; font-variant: normal; font-weight: normal; font-size: 7pt; line-height: normal; font-size-adjust: none; font-stretch: normal;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span></span></span></strong><!--[endif]--><strong><span style="font-size: 14pt; font-family: 宋体; color: purple;">复制</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US">RAII</span></strong><strong><span style="font-size: 14pt; font-family: 宋体; color: purple;">对象必须一并复制它所管理的资源，所以资源的</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US">copying</span></strong><strong><span style="font-size: 14pt; font-family: 宋体; color: purple;">行为决定</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US">RAII</span></strong><strong><span style="font-size: 14pt; font-family: 宋体; color: purple;">对象的</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US">copying</span></strong><strong><span style="font-size: 14pt; font-family: 宋体; color: purple;">行为。</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US"><o:p></o:p></span></strong></p>
<p class="MsoNormal" style="margin-left: 18pt; text-indent: -18pt;"><!--[if !supportLists]--><strong><span style="font-size: 14pt; color: purple;" lang="EN-US"><span>2、<span style="font-family: &quot;Times New Roman&quot;; font-style: normal; font-variant: normal; font-weight: normal; font-size: 7pt; line-height: normal; font-size-adjust: none; font-stretch: normal;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
</span></span></span></strong><!--[endif]--><strong><span style="font-size: 14pt; font-family: 宋体; color: purple;">普遍而常见的</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US">RAII class copying</span></strong><strong><span style="font-size: 14pt; font-family: 宋体; color: purple;">行为是：抑制</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US">copying</span></strong><strong><span style="font-size: 14pt; font-family: 宋体; color: purple;">、施行引用计数法。不过其他行为也都可能被实现。</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US"><o:p></o:p></span></strong></p><img src ="http://www.cppblog.com/yugong/aggbug/37475.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/yugong/" target="_blank">Nathan.Yu</a> 2007-11-29 00:43 <a href="http://www.cppblog.com/yugong/articles/37475.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Effective C++读书笔记—3 资源管理(之1)</title><link>http://www.cppblog.com/yugong/articles/37406.html</link><dc:creator>Nathan.Yu</dc:creator><author>Nathan.Yu</author><pubDate>Tue, 27 Nov 2007 16:50:00 GMT</pubDate><guid>http://www.cppblog.com/yugong/articles/37406.html</guid><wfw:comment>http://www.cppblog.com/yugong/comments/37406.html</wfw:comment><comments>http://www.cppblog.com/yugong/articles/37406.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/yugong/comments/commentRss/37406.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/yugong/services/trackbacks/37406.html</trackback:ping><description><![CDATA[<h1 style="margin: 17pt 0cm 16.5pt; text-align: center;" align="center"><font size="6"><font color="#000000"><span lang="EN-US"><font face="Times New Roman">Effective C++</font></span><span style="font-family: 宋体;">读书笔记</span></font></font></h1>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt 210pt; text-indent: 21pt;"><em><span style="font-size: 14pt;" lang="EN-US">--By Nathan.Yu 2007-11-27--<o:p></o:p></span></em></p>
<h2 style="margin: 13pt 0cm;"><font size="5"><font color="#000000"><span lang="EN-US"><font face="Arial">3 </font></span><span style="font-family: 黑体;">资源管理</span><span lang="EN-US"><font face="Arial">(</font></span><span style="font-family: 黑体;">之一</span><span lang="EN-US"><font face="Arial">)</font></span></font></font></h2>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span style="font-family: 宋体;">常见的资源：<span style="color: blue;">文件描述器（</span></span><span style="color: blue;" lang="EN-US">file descriptors</span><span style="color: blue; font-family: 宋体;">）</span><span style="font-family: 宋体;">、<span style="color: blue;">互斥锁（</span></span><span style="color: blue;" lang="EN-US">mutex locks</span><span style="color: blue; font-family: 宋体;">）</span><span style="font-family: 宋体;">、<span style="color: blue;">图形界面中的字型和笔刷</span>、<span style="color: blue;">数据库连接</span>、<span style="color: blue;">网络</span></span><span style="color: blue;" lang="EN-US">sockets</span><span style="color: blue; font-family: 宋体;">。</span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span lang="EN-US"><o:p>&nbsp;</o:p></span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span style="color: red; font-family: 宋体;">不论哪一种资源，重要的是，当你不再使用它时，必须将它还给系统。</span><span style="color: red;" lang="EN-US"><o:p></o:p></span></p>
<h3 style="margin: 13pt 0cm;"><font size="5"><span style="font-family: 宋体;">条款</span><span lang="EN-US">13</span><span style="font-family: 宋体;">：以对象管理资源（</span><span lang="EN-US">Use objects to manage resources</span><span style="font-family: 宋体;">）</span></font></h3>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span lang="EN-US">auto_ptr</span><span style="font-family: 宋体;">是一个&#8220;类指针</span><span lang="EN-US">(pointer-like)</span><span style="font-family: 宋体;">对象&#8221;，也就是所谓的&#8220;智能指针&#8221;，其析构函数自动对其所指对象调用</span><span lang="EN-US">delete</span><span style="font-family: 宋体;">。</span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span lang="EN-US">RAII</span><span style="font-family: 宋体;">（</span><span lang="EN-US">Resource Acquisition Is Initialization</span><span style="font-family: 宋体;">）：资源取得即初始化。</span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span lang="EN-US"><o:p>&nbsp;</o:p></span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span lang="EN-US">&lt;</span><span style="color: red; font-family: 宋体;">注意</span><span lang="EN-US">&gt;</span><span style="font-family: 宋体;">由于</span><span lang="EN-US">auto_ptr</span><span style="font-family: 宋体;">被销毁时会自动删除它所指之物，所以别让多个</span><span lang="EN-US">auto_ptr</span><span style="font-family: 宋体;">同时指向同一对象。为了预防这个问题，</span><span lang="EN-US">auto_ptrs</span><span style="font-family: 宋体;">有一个不寻常的<span style="color: green;">性质</span>：</span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span lang="EN-US"><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span><span style="color: blue; font-family: 宋体;">若通过</span><span style="color: blue;" lang="EN-US">copy</span><span style="color: blue; font-family: 宋体;">构造函数或</span><span style="color: blue;" lang="EN-US">copy assignment</span><span style="color: blue; font-family: 宋体;">操作符复制它们，它们会变成</span><span style="color: blue;" lang="EN-US">null</span><span style="color: blue; font-family: 宋体;">，而复制所得的指针将取得资源的唯一拥有权！</span><span style="color: blue;" lang="EN-US"><o:p></o:p></span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span style="font-family: 宋体;">由于这一诡异的复制行为，加上&#8220;受</span><span lang="EN-US">auto_ptrs</span><span style="font-family: 宋体;">管理的资源必须绝对没有一个以上的</span><span lang="EN-US">auto_ptr</span><span style="font-family: 宋体;">同时指向它&#8221;，意味着</span><span lang="EN-US">auto_ptr</span><span style="font-family: 宋体;">并非管理动态分配资源的神兵利器。</span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span lang="EN-US"><span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span><span style="color: red;">STL</span></span><span style="color: red; font-family: 宋体;">容器要求其元素发挥&#8220;正常&#8221;赋值行为，因此不能用</span><span style="color: red;" lang="EN-US">auto_ptr</span><span style="color: red; font-family: 宋体;">管理它们。</span><span style="color: red;" lang="EN-US"><o:p></o:p></span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span lang="EN-US"><o:p>&nbsp;</o:p></span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span lang="EN-US">auto_ptr</span><span style="font-family: 宋体;">的替代方案是&#8220;引用计数型智能指针&#8221;</span><span lang="EN-US">(reference-counting smart pointer, RCSP)</span><span style="font-family: 宋体;">。</span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span lang="EN-US">RCSPs</span><span style="font-family: 宋体;">提供的行为类似垃圾回收</span><span lang="EN-US">(GC, garbage collection)</span><span style="font-family: 宋体;">，不同的是</span><span lang="EN-US">RCSPs</span><span style="font-family: 宋体;">无法打破环状引用（</span><span lang="EN-US">cycles of reference</span><span style="font-family: 宋体;">，</span> <span style="font-family: 宋体;">例如两个其实已经没被使用的对象彼此互指，好像还处在&#8220;被使用&#8221;状态）。</span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span lang="EN-US">RCSPs</span><span style="font-family: 宋体;">举例：</span><span lang="EN-US">tr1</span><span style="font-family: 宋体;">：：</span><span lang="EN-US">shared_ptr</span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span lang="EN-US"><o:p>&nbsp;</o:p></span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span lang="EN-US">&lt;</span><span style="color: red; font-family: 宋体;">注意</span><span lang="EN-US">&gt;auto_ptr</span><span style="font-family: 宋体;">和</span><span lang="EN-US">tr1</span><span style="font-family: 宋体;">：：</span><span lang="EN-US">shared_ptr</span><span style="font-family: 宋体;">两者都在析构函数内做</span><span lang="EN-US">delete</span><span style="font-family: 宋体;">而不是</span><span lang="EN-US">delete[]</span><span style="font-family: 宋体;">动作。意味着两者都不能用在动态分配的数组上。</span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span style="font-family: 宋体;">对数组可用容器如</span><span lang="EN-US">vector</span><span style="font-family: 宋体;">等代替。</span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span style="font-family: 宋体;">然，</span><span lang="EN-US">boost::scoped_array</span><span style="font-family: 宋体;">和</span><span lang="EN-US">boost::shared_array</span><span style="font-family: 宋体;">则提供了上述管理数组的能力。</span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span lang="EN-US"><o:p>&nbsp;</o:p></span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt;"><span style="color: red; font-family: 宋体;">请记住：</span><span style="color: red;" lang="EN-US"><o:p></o:p></span></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt 18pt; text-indent: -18pt;"><strong><span style="font-size: 14pt; color: purple;" lang="EN-US"><span>1、<span style="font-family: 'Times New Roman'; font-style: normal; font-variant: normal; font-weight: normal; font-size: 7pt; line-height: normal; font-size-adjust: none; font-stretch: normal;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span></span></strong><strong><span style="font-size: 14pt; color: purple; font-family: 宋体;">为防止资源泄漏，请使用</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US">RAII</span></strong><strong><span style="font-size: 14pt; color: purple; font-family: 宋体;">对象，它们在构造函数中获得资源并在析构函数中释放资源。</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US"><o:p></o:p></span></strong></p>
<p class="MsoNormal" style="margin: 0cm 0cm 0pt 18pt; text-indent: -18pt;"><strong><span style="font-size: 14pt; color: purple;" lang="EN-US"><span>2、<span style="font-family: 'Times New Roman'; font-style: normal; font-variant: normal; font-weight: normal; font-size: 7pt; line-height: normal; font-size-adjust: none; font-stretch: normal;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span></span></strong><strong><span style="font-size: 14pt; color: purple; font-family: 宋体;">两个被使用的</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US">RAII classes</span></strong><strong><span style="font-size: 14pt; color: purple; font-family: 宋体;">分别是</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US">tr1::shared_ptr</span></strong><strong><span style="font-size: 14pt; color: purple; font-family: 宋体;">和</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US">auto_ptr</span></strong><strong><span style="font-size: 14pt; color: purple; font-family: 宋体;">。前者通常是较佳选择，因为其</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US">copy</span></strong><strong><span style="font-size: 14pt; color: purple; font-family: 宋体;">行为比较直观。若选择</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US">auto_ptr</span></strong><strong><span style="font-size: 14pt; color: purple; font-family: 宋体;">，复制动作会使它（被复制物）指向</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US">null</span></strong><strong><span style="font-size: 14pt; color: purple; font-family: 宋体;">。</span></strong><strong><span style="font-size: 14pt; color: purple;" lang="EN-US"><o:p></o:p></span></strong></p><img src ="http://www.cppblog.com/yugong/aggbug/37406.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/yugong/" target="_blank">Nathan.Yu</a> 2007-11-28 00:50 <a href="http://www.cppblog.com/yugong/articles/37406.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Effective C++读书笔记—2 构造、析构、赋值运算(之4)</title><link>http://www.cppblog.com/yugong/articles/37360.html</link><dc:creator>Nathan.Yu</dc:creator><author>Nathan.Yu</author><pubDate>Mon, 26 Nov 2007 16:55:00 GMT</pubDate><guid>http://www.cppblog.com/yugong/articles/37360.html</guid><wfw:comment>http://www.cppblog.com/yugong/comments/37360.html</wfw:comment><comments>http://www.cppblog.com/yugong/articles/37360.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/yugong/comments/commentRss/37360.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/yugong/services/trackbacks/37360.html</trackback:ping><description><![CDATA[<h1 style="MARGIN: 17pt 0cm 16.5pt; TEXT-ALIGN: center" align=center><font size=6><font color=#000000><span lang=EN-US><font face="Times New Roman">Effective C++</font></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">读书笔记</span></font></font></h1>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 210pt; TEXT-INDENT: 21pt"><em style="mso-bidi-font-style: normal"><span lang=EN-US style="FONT-SIZE: 14pt">--By Nathan.Yu 2007-11-24--<o:p></o:p></span></em></p>
<h2 style="MARGIN: 13pt 0cm"><font size=5><font color=#000000><span lang=EN-US><font face=Arial>2 </font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">构造</span><span lang=EN-US><font face=Arial>/</font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">析构</span><span lang=EN-US><font face=Arial>/</font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">赋值运算</span><span lang=EN-US><font face=Arial>(</font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">之四</span><span lang=EN-US><font face=Arial>)</font></span></font></font></h2>
<h3 style="MARGIN: 13pt 0cm"><font size=5><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">条款</span><span lang=EN-US>08</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：别让异常逃离析构函数</span></font></h3>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 16pt; COLOR: red">C++</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 16pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">并不禁止析构函数吐出异常，但它不鼓励你这样做</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 16pt; COLOR: red">!<o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">理由：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">设：</span><span lang=EN-US>std::vector&lt;Widget&gt; v;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">假设</span><span lang=EN-US>v</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">中有多个</span><span lang=EN-US>Widget</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，在销毁</span><span lang=EN-US>v</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的过程中，当有</span><span lang=EN-US>2</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">个以上的</span><span lang=EN-US>Widget</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">在销毁的时候抛出异常，对</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">而言就太多了。在两个异常同时存在的情况下，程序若不是结束执行就是导致不明确行为。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">只要是在析构函数吐出异常，即使并非使用容器，程序也可能过早结束或出现不明确行为。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">如果程序在析构函数中捕获异常，&#8220;强迫结束程序，即调用</span><span lang=EN-US>abort</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">&#8221;是个合理的选项。可以抢先制&#8220;不明确行为&#8221;于死地。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">另，将异常吞没是个坏主意。因为它压制了&#8220;某些动作失败&#8221;的重要信息。为了让这成为一个可行的方案，程序必须确保能够继续可靠地执行，即使在遭遇并忽略一个错误之后。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">更好地做法是，赋予客户一个处理异常的机会。如果某个操作必须在析构函数中使用，它又可能抛出异常，则将这个操作作为一个公共的接口，允许客户手动调用，让客户自处理异常。在析构函数中，判断客户是否调用过该函数，如若没有，则再次调用，并对可能抛出的异常进行处理。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">总之，如果某个操作可能在失败时抛出异常，而又存在某种需要必须处理该异常，那么这个异常必须来自析构函数以外的某个函数。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">请记住：</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt; TEXT-INDENT: -18pt; mso-list: l2 level1 lfo1; tab-stops: list 18.0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple; mso-fareast-font-family: 'Times New Roman'"><span style="mso-list: Ignore">1、<span style="FONT: 7pt 'Times New Roman'">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span></span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数绝对不要吐出异常。如果一个被析构函数调用的函数可能抛出异常，析构函数应该捕捉任何异常，然后吞下它或结束程序。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt; TEXT-INDENT: -18pt; mso-list: l2 level1 lfo1; tab-stops: list 18.0pt"><span lang=EN-US style="mso-fareast-font-family: 'Times New Roman'"><span style="mso-list: Ignore">2、<span style="FONT: 7pt 'Times New Roman'">&nbsp; </span></span></span><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">如果客户需要对某个操作函数运行期间抛出的异常做出反应，那么</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">class</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">应该提供一个普通函数（而非在析构函数中）执行该操作</span></strong><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">【备注】参见</span><span lang=EN-US style="COLOR: red">More Effective C++</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：</span> <span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">条款十一：禁止异常信息（</span><span lang=EN-US style="COLOR: blue">exceptions</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）传递到析构函数外</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<h3 style="MARGIN: 13pt 0cm"><font size=5><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">条款</span><span lang=EN-US>09</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：绝不在构造和析构过程中调用</span><span lang=EN-US>virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数</span></font></h3>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: red">&lt;</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">注意</span><span lang=EN-US style="COLOR: red">&gt;</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">这是</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">与</span><span lang=EN-US>Java</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">或</span><span lang=EN-US>C#</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">不同的一个地方</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>1</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、</span><span lang=EN-US>Base class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造期间</span><span lang=EN-US>virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数绝不会下降到</span><span lang=EN-US>derived classes</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">阶层。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>2</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、在</span><span lang=EN-US>base class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造期间，</span><span lang=EN-US>virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数不是</span><span lang=EN-US>virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: blue">3</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、在</span><span lang=EN-US style="COLOR: blue">derived class</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象的</span><span lang=EN-US style="COLOR: blue">base class</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造期间，对象的类型是</span><span lang=EN-US style="COLOR: blue">base class</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">而不是</span><span lang=EN-US style="COLOR: blue">derived class</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。因此，不止</span><span lang=EN-US style="COLOR: blue">vritual</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数会被编译器解析为</span><span lang=EN-US style="COLOR: blue">base class</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，若使用运行期类型信息（如</span><span lang=EN-US style="COLOR: blue">dynamic_cast</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">或</span><span lang=EN-US style="COLOR: blue">typeid</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">），也会把对象视为</span><span lang=EN-US style="COLOR: blue">base class</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">类型。</span><span lang=EN-US style="COLOR: blue"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>4</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、对象在</span><span lang=EN-US>derived class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数开始执行前不会成为一个</span><span lang=EN-US>derived class </span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">相同道理也适用于析构函数。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">解决方案：改用</span><span lang=EN-US>non-virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数，并要求</span><span lang=EN-US>derived class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数传递必要信息给</span><span lang=EN-US>base class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数，</span><span lang=EN-US>base class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数中调用</span><span lang=EN-US>non-virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，该函数根据不同的信息处理不同的</span><span lang=EN-US>derived class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">请记住：</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">在构造和析构期间不要调用</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">virtual</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数，因为这类调用从不下降至</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">derived class</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<h3 style="MARGIN: 13pt 0cm"><font size=5><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">条款</span><span lang=EN-US>10</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：令</span><span lang=EN-US>operator=</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">返回一个</span><span lang=EN-US>reference to *this</span></font></h3>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 15pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">协议：</span></strong><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">为了实现</span><span lang=EN-US style="COLOR: blue">x=y=z=15</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">之类的&#8220;</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">连锁赋值</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">&#8221;，赋值操作符必须返回一个引用指向操作符的左侧实参。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">这个协议<span style="COLOR: red">适合于所有赋值相关运算</span>（</span><span lang=EN-US>operator op=</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">请记住：</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">令赋值（</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">assignment</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）操作符返回一个</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">reference to *this</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<h3 style="MARGIN: 13pt 0cm"><font size=5><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">条款</span><span lang=EN-US>11</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：在</span><span lang=EN-US>operator=</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">中处理&#8220;自我赋值&#8221;</span></font></h3>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">什么情况发生&#8220;自我赋值&#8221;？</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: red"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">情况</span><span lang=EN-US style="COLOR: blue">1</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：</span><span lang=EN-US>Widget w;<span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>w = w;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">情况</span><span lang=EN-US style="COLOR: blue">2</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：</span><span lang=EN-US>a[i] = a[j]; //</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">潜在的自我赋值，当</span><span lang=EN-US>i == j</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">时</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">情况</span><span lang=EN-US style="COLOR: blue">3</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：</span><span lang=EN-US>*px = *py; //px</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、</span><span lang=EN-US>py</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">恰巧指向同一个对象。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">详细分析</span><span lang=EN-US>operator=</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">时可能出现的情况：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">假设类：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>class Bitmap{&#8230;&#8230;};</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>class Widget{</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>&#8230;&#8230;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>private:</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>Bitmap* pb;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>};</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>operator=</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的不同实现版本：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">版本</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: red">1</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：</span></strong><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">一份不安全的实现版本，不具&#8220;自我赋值安全性&#8221;，不具&#8220;异常安全性&#8221;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>Widget&amp; </span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>Widget::operator=(const Widget&amp; rhs)</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>{</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span><st1:state w:st="on"><st1:place w:st="on">del</st1:place></st1:state>ete pb;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>pb = new Bitmap(*rhs.pb);</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>return *this;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>}</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">这里的自我赋值是，</span><span lang=EN-US>*this</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">和</span><span lang=EN-US>rhs</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">有可能是同一个对象。果真如此</span><span lang=EN-US>delete</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">就不只是销毁当前对象的</span><span lang=EN-US>bitmap</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">了，也销毁</span><span lang=EN-US>rhs</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的</span><span lang=EN-US>pb</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。那么</span><span lang=EN-US>*this</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">将持有一个已被删除的对象。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">版本</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: red">2</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：</span></strong><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">使用&#8220;证同测试</span><span lang=EN-US>(Identity test)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">&#8221;阻止版本</span><span lang=EN-US>1</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">中的错误，达到&#8220;自我赋值&#8221;的检测目的，具&#8220;自我赋值安全性&#8221;，不具&#8220;异常安全性&#8221;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>Widget&amp; </span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>Widget::operator=(const Widget&amp; rhs)</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>{</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>if(this == &amp;rhs) return *this;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span><st1:state w:st="on"><st1:place w:st="on">del</st1:place></st1:state>ete pb;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>pb = new Bitmap(*rhs.pb);</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>return *this;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>}</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">这里，</span><span lang=EN-US>new Bitmap</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">可能导致异常（不论是因为分配内存不足或因为</span><span lang=EN-US>Bitmap</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的拷贝构造抛出异常），</span><span lang=EN-US>Widget</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">会持有一个指针指向一块被删除的</span><span lang=EN-US>Bitmap</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">版本</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: red">3</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：</span></strong><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">忽视&#8220;自我赋值&#8221;，把焦点放在实现&#8220;异常安全性上&#8221;，因为让</span><span lang=EN-US>operator=</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">具备&#8220;异常安全&#8221;往往自动获得&#8220;自我赋值安全&#8221;的回报。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: red">&lt;</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">注意</span><span lang=EN-US style="COLOR: red">&gt;</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">&#8220;许多时候一群精心安排的语句就可以导出异常安全（以及自我赋值安全）的代码&#8221;</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，例如：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>Widget&amp; </span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>Widget::operator=(const Widget&amp; rhs)</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>{</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>Bitmap* <st1:city w:st="on"><st1:place w:st="on">pOri</st1:place></st1:city>g = pb; //</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">记住原先的</span><span lang=EN-US>pb</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>pb = new Bitmap(*rhs.pb); // </span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">令</span><span lang=EN-US>pb</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">指向</span><span lang=EN-US>*pb</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的一个副本</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span><st1:state w:st="on">del</st1:state>ete <st1:city w:st="on"><st1:place w:st="on">pOri</st1:place></st1:city>g; //</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">删除原先的</span><span lang=EN-US>pb</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>return *this;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>}</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">它或许不是处理&#8220;自我赋值&#8221;的最高效办法，但它行得通。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">版本</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: red">4</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：</span></strong><span lang=EN-US style="COLOR: blue">copy and swap</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">技术</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，处理&#8220;自我赋值&#8221;的一个简单而通用的技术，并且是&#8220;异常安全的&#8221;（该版本的详细讨论可参考</span><span lang=EN-US>Exceptional C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>Widget&amp; </span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>Widget::operator=(const Widget&amp; rhs)</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>{</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>Widget temp(rhs);</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>swap(temp);</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>return *this;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>}</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">请记住</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt; TEXT-INDENT: -18pt; mso-list: l1 level1 lfo2; tab-stops: list 18.0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple; mso-fareast-font-family: 'Times New Roman'"><span style="mso-list: Ignore">1、<span style="FONT: 7pt 'Times New Roman'">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span></span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">确保当对象自我赋值时</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">operator=</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">有良好的行为。其中技术包括比较&#8220;来源对象&#8221;和&#8220;目标对象&#8221;的地址、精心周到的语句顺序、以及</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">copy-and-swap</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt; TEXT-INDENT: -18pt; mso-list: l1 level1 lfo2; tab-stops: list 18.0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple; mso-fareast-font-family: 'Times New Roman'"><span style="mso-list: Ignore">2、<span style="FONT: 7pt 'Times New Roman'">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span></span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">确定任何函数如果操作一个以上的对象，而其中多个对象是同一个对象时，其行为仍然正常。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<h3 style="MARGIN: 13pt 0cm"><font size=5><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">条款</span><span lang=EN-US>12</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：复制对象时勿忘其每一个成分</span></font></h3>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">如果你为</span><span lang=EN-US>class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">添加一个成员变量，你必须同时修改</span><span lang=EN-US>copying</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数</span><span lang=EN-US>(copy</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造，</span><span lang=EN-US>copy</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">赋值</span><span lang=EN-US>)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，也需要修改所有其他构造函数以及任何非标准形式的</span><span lang=EN-US>operator=</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">任何时候只要你承担起&#8220;为</span><span lang=EN-US style="COLOR: blue">derived class</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">撰写</span><span lang=EN-US style="COLOR: blue">copying</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数&#8221;的重责大任，必须很小心的复制其</span><span lang=EN-US style="COLOR: blue">base class</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成分。那些成分往往是</span><span lang=EN-US style="COLOR: blue">private</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的，所以你无法直接访问它们，你应该让</span><span lang=EN-US style="COLOR: blue">derived class</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的</span><span lang=EN-US style="COLOR: blue">copying</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数调用相应的</span><span lang=EN-US style="COLOR: blue">base class</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数。</span><span lang=EN-US style="COLOR: blue"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">能否令某个</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: red">copying</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数调用另一个</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: red">copying</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数？</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">不能！</span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">令</span><span lang=EN-US>copy assignment</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">操作符调用</span><span lang=EN-US>copy</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数是不合理的，因为这就像试图构造一个已经存在的对象。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">令</span><span lang=EN-US>copy</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数调用</span><span lang=EN-US>copy</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">赋值操作符同样无意义。构造函数用来初始化新对象，而赋值操作符只施加于已初始化对象身上。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">使用</span><span lang=EN-US style="COLOR: blue">private</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的函数</span><span lang=EN-US style="COLOR: blue">init()</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">来消除重复代码。</span><span lang=EN-US style="COLOR: blue"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">请记住：</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 36pt; TEXT-INDENT: -36pt; mso-list: l0 level1 lfo3; tab-stops: list 36.0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple; mso-fareast-font-family: 'Times New Roman'"><span style="mso-list: Ignore">1、<span style="FONT: 7pt 'Times New Roman'">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span></span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">copying</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数应该确保复制&#8220;对象内的所有成员变量&#8221;及&#8220;所有</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">base class</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成分&#8221;。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 36pt; TEXT-INDENT: -36pt; mso-list: l0 level1 lfo3; tab-stops: list 36.0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple; mso-fareast-font-family: 'Times New Roman'"><span style="mso-list: Ignore">2、<span style="FONT: 7pt 'Times New Roman'">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span></span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">不要尝试以某个</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">copying</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数实现另一个</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">copying</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数。应该将共同机能放进第三个函数中，并由两个</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">copying</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数共同调用。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<img src ="http://www.cppblog.com/yugong/aggbug/37360.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/yugong/" target="_blank">Nathan.Yu</a> 2007-11-27 00:55 <a href="http://www.cppblog.com/yugong/articles/37360.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Effective C++读书笔记—2 构造、析构、赋值运算(之3)</title><link>http://www.cppblog.com/yugong/articles/37359.html</link><dc:creator>Nathan.Yu</dc:creator><author>Nathan.Yu</author><pubDate>Mon, 26 Nov 2007 16:54:00 GMT</pubDate><guid>http://www.cppblog.com/yugong/articles/37359.html</guid><wfw:comment>http://www.cppblog.com/yugong/comments/37359.html</wfw:comment><comments>http://www.cppblog.com/yugong/articles/37359.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/yugong/comments/commentRss/37359.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/yugong/services/trackbacks/37359.html</trackback:ping><description><![CDATA[<h1 style="MARGIN: 17pt 0cm 16.5pt; TEXT-ALIGN: center" align=center><font size=6><font color=#000000><span lang=EN-US><font face="Times New Roman">Effective C++</font></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">读书笔记</span></font></font></h1>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 210pt; TEXT-INDENT: 21pt"><em style="mso-bidi-font-style: normal"><span lang=EN-US style="FONT-SIZE: 14pt">--By Nathan.Yu 2007-11-15--<o:p></o:p></span></em></p>
<h2 style="MARGIN: 13pt 0cm"><font size=5><font color=#000000><span lang=EN-US><font face=Arial>2 </font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">构造</span><span lang=EN-US><font face=Arial>/</font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">析构</span><span lang=EN-US><font face=Arial>/</font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">赋值运算</span><span lang=EN-US><font face=Arial>(</font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">之三</span><span lang=EN-US><font face=Arial>)</font></span></font></font></h2>
<h3 style="MARGIN: 13pt 0cm"><font size=5><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">条款</span><span lang=EN-US>07</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：为多态基类声明</span><span lang=EN-US>virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数</span></font></h3>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 16pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">问题：何时该声明</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 16pt; COLOR: red">virtual</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 16pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数，何时不该这样做？</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 16pt; COLOR: red"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">【要点摘录】</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">明确指出，当</span><span lang=EN-US>derived class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象经由一个</span><span lang=EN-US>base class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">指针被删除，而该</span><span lang=EN-US>base class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">带着一个</span><span lang=EN-US>non-virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数，其结果未有定义——实际执行时常发生的是对象的</span><span lang=EN-US>derived</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成分没被销毁。造成&#8220;局部销毁&#8221;对象。消除这个问题的做法很简单：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 12pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">给</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 12pt; COLOR: red">base class</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 12pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">一个</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 12pt; COLOR: red">virtual</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 12pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 12pt; COLOR: red"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">任何</span><span lang=EN-US style="COLOR: blue">class</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">只要带有</span><span lang=EN-US style="COLOR: blue">virtual</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数都几乎确定应该也有一个</span><span lang=EN-US style="COLOR: blue">virtual</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数。</span><span lang=EN-US style="COLOR: blue"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">如果</span><span lang=EN-US style="COLOR: green">class</span><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">不含</span><span lang=EN-US style="COLOR: green">virtual</span><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数，通常表示它并不意图被用做一个</span><span lang=EN-US style="COLOR: green">base class</span><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">当</span><span lang=EN-US>class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">不企图当作</span><span lang=EN-US>base class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，令其析构函数为</span><span lang=EN-US>virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">往往是个馊主意。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">无端的将</span><span lang=EN-US>classes</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对析构函数声明为</span><span lang=EN-US>virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，就像从未声明它们为</span><span lang=EN-US>virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">一样，都是错误的。<span style="COLOR: blue">许多人都心得是：</span></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 12pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">只有当</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 12pt; COLOR: red">class</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 12pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">内至少含一个</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 12pt; COLOR: red">virtual</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 12pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数，才为他声明</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 12pt; COLOR: red">virtual</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 12pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 12pt; COLOR: red"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">如果你曾经企图继承（作为多态继承，一般是</span><span lang=EN-US>public</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">继承）一个标准容器或任何其他&#8220;带有</span><span lang=EN-US>non-virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数&#8221;的</span><span lang=EN-US>class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，拒绝诱惑吧！（很不幸，</span><span lang=EN-US style="COLOR: green">C++</span><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">没有提供类似</span><span lang=EN-US style="COLOR: green">Java</span><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的</span><span lang=EN-US style="COLOR: green">final classes</span><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">或</span><span lang=EN-US style="COLOR: green">C#</span><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的</span><span lang=EN-US style="COLOR: green">sealed class</span><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">那样的&#8220;禁止派生&#8221;机制</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">当你需要一个抽象类，但没有任何可用的</span><span lang=EN-US>pure virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">时（可能是其他的</span><span lang=EN-US>virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数都有默认实现），可以声明一个</span><span lang=EN-US>pure virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数。因为，抽象类总是企图被当作一个</span><span lang=EN-US>base class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">来用，做为</span><span lang=EN-US>base class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">就必须有个</span><span lang=EN-US>virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数，而</span><span lang=EN-US>pure virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">导致抽象类，因此可以声明一个</span><span lang=EN-US>pure virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数，使其成为抽象类。但<span style="COLOR: blue">必须为这个</span></span><span lang=EN-US style="COLOR: blue">pure virtual</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数提供一份定义，否则会发生链接错误</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。因为在销毁派生对象时，最终会调用这个抽象类的析构函数。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">&#8220;给</span><span lang=EN-US>base classes</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">一个</span><span lang=EN-US>virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数&#8221;，这个规则只适用于带多态性质的</span><span lang=EN-US>base classes</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">身上。这种</span><span lang=EN-US>base classes</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的设计目的是为了用来&#8220;通过</span><span lang=EN-US>base class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">接口处理</span><span lang=EN-US>derived class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象&#8221;。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">并非所有的</span><span lang=EN-US>base class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的设计目的都是为了多态用途的。某些类的设计目的是仅仅作为基类实现代码复用，但不是为了多态用途（它们没有任何</span><span lang=EN-US>virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数），由于它们</span><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 12pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">不被设计用来&#8220;经由</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 12pt; COLOR: red">base class</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 12pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">接口处置</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 12pt; COLOR: red">derived class </span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 12pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象&#8221;，因此它们不需要</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 12pt; COLOR: red">virtual</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 12pt; COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数。</span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">请记住：</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt; TEXT-INDENT: -18pt; mso-list: l0 level1 lfo1; tab-stops: list 18.0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple; mso-fareast-font-family: 'Times New Roman'"><span style="mso-list: Ignore">1、<span style="FONT: 7pt 'Times New Roman'">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span></span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">polymorphic(</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">带多态性质的</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">)base classes </span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">应该声明一个</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">virtual</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数。如果</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">class </span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">带有任何</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">virtual</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数，它就应该拥有一个</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">virtual</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt; TEXT-INDENT: -18pt; mso-list: l0 level1 lfo1; tab-stops: list 18.0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple; mso-fareast-font-family: 'Times New Roman'"><span style="mso-list: Ignore">2、<span style="FONT: 7pt 'Times New Roman'">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span></span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">Classes</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的设计目的如果不是作为</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">base classes</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">使用，或不是为了具备多态</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">(polymorphically)</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，就不该声明</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">virtual</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<img src ="http://www.cppblog.com/yugong/aggbug/37359.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/yugong/" target="_blank">Nathan.Yu</a> 2007-11-27 00:54 <a href="http://www.cppblog.com/yugong/articles/37359.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Effective C++读书笔记—2 构造、析构、赋值运算(之2)</title><link>http://www.cppblog.com/yugong/articles/37358.html</link><dc:creator>Nathan.Yu</dc:creator><author>Nathan.Yu</author><pubDate>Mon, 26 Nov 2007 16:53:00 GMT</pubDate><guid>http://www.cppblog.com/yugong/articles/37358.html</guid><wfw:comment>http://www.cppblog.com/yugong/comments/37358.html</wfw:comment><comments>http://www.cppblog.com/yugong/articles/37358.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/yugong/comments/commentRss/37358.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/yugong/services/trackbacks/37358.html</trackback:ping><description><![CDATA[<h1 style="MARGIN: 17pt 0cm 16.5pt; TEXT-ALIGN: center" align=center><font size=6><font color=#000000><span lang=EN-US><font face="Times New Roman">Effective C++</font></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">读书笔记</span></font></font></h1>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 210pt; TEXT-INDENT: 21pt"><em style="mso-bidi-font-style: normal"><span lang=EN-US style="FONT-SIZE: 14pt">--By Nathan.Yu 2007-11-14--<o:p></o:p></span></em></p>
<h2 style="MARGIN: 13pt 0cm"><font size=5><font color=#000000><span lang=EN-US><font face=Arial>2 </font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">构造</span><span lang=EN-US><font face=Arial>/</font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">析构</span><span lang=EN-US><font face=Arial>/</font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">赋值运算</span><span lang=EN-US><font face=Arial>(</font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">之二</span><span lang=EN-US><font face=Arial>)</font></span></font></font></h2>
<h3 style="MARGIN: 13pt 0cm"><font size=5><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">条款</span><span lang=EN-US>06</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：若不想使用编译器自动生成的函数，就该明确拒绝</span></font></h3>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">【要点摘录】所有编译器生成的函数都是</span><span lang=EN-US>public</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">且</span><span lang=EN-US>inline</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">如何阻止拷贝行为？</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">将</span><span lang=EN-US>copy</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数和</span><span lang=EN-US>copy assignment</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">操作符声明为</span><span lang=EN-US>private</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，并不去定义（实现）它们。借由明确声明一个成员函数，阻止了编译器暗自创建其专属版本；而令这些函数为</span><span lang=EN-US>private</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，可以阻止人们调用它；只声明而不实现，则如果在成员函数或</span><span lang=EN-US>friend</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数中调用它们，会产生链接错误。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">【扩展】</span><span lang=EN-US>C++ iostream</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">就是使用这个方法来组织</span><span lang=EN-US>copying</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">行为的。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">一个更好的方法：</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">把链接期错误移至编译期，并可复用代码。即使用</span><span lang=EN-US>Uncopyable base class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">阻止拷贝：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>class Uncopyable{</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>protected:<span style="mso-spacerun: yes">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>//</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">允许</span><span lang=EN-US>derived</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象构造和析构</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>Uncopyable(){}</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">～</span><span lang=EN-US>Uncopyable(){} //</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">不一定得是</span><span lang=EN-US>virtual</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: red">private:<o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>Uncopyable(const Uncopyable&amp;)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">；</span><span lang=EN-US>//</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">阻止</span><span lang=EN-US>copying</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>Uncopyable&amp; operator=(const Uncopyable&amp;)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">；</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>};</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>/*</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">不含数据成员，符合</span><span lang=EN-US>EBO(empty base class optimization)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">资格</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">总是扮演</span><span lang=EN-US>base class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">角色，导致多重继承。而多重继承有时会阻止</span><span lang=EN-US>EBO</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>Boost</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">版本：</span><span lang=EN-US>noncopyable</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>*/</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>class MyClass:<span style="COLOR: red"> private </span><span style="COLOR: blue">Uncopyable</span>{ // </span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">使用私有继承</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>&#8230;&#8230;&#8230;..</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>};</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">请记住：</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">为驳回编译器自动提供的机制，可将相应的成员函数声明为</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">private</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">并且不予实现。使用像</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">Uncopyable</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">这样的</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">base class</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">也是一种做法。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<img src ="http://www.cppblog.com/yugong/aggbug/37358.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/yugong/" target="_blank">Nathan.Yu</a> 2007-11-27 00:53 <a href="http://www.cppblog.com/yugong/articles/37358.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Effective C++读书笔记—2 构造、析构、赋值运算(之1)</title><link>http://www.cppblog.com/yugong/articles/37357.html</link><dc:creator>Nathan.Yu</dc:creator><author>Nathan.Yu</author><pubDate>Mon, 26 Nov 2007 16:52:00 GMT</pubDate><guid>http://www.cppblog.com/yugong/articles/37357.html</guid><wfw:comment>http://www.cppblog.com/yugong/comments/37357.html</wfw:comment><comments>http://www.cppblog.com/yugong/articles/37357.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/yugong/comments/commentRss/37357.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/yugong/services/trackbacks/37357.html</trackback:ping><description><![CDATA[<h1 style="MARGIN: 17pt 0cm 16.5pt; TEXT-ALIGN: center" align=center><font size=6><font color=#000000><span lang=EN-US><font face="Times New Roman">Effective C++</font></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">读书笔记</span></font></font></h1>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 210pt; TEXT-INDENT: 21pt"><em style="mso-bidi-font-style: normal"><span lang=EN-US style="FONT-SIZE: 14pt">--By Nathan.Yu 2007-11-13--<o:p></o:p></span></em></p>
<h2 style="MARGIN: 13pt 0cm"><font size=5><font color=#000000><span lang=EN-US><font face=Arial>2 </font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">构造</span><span lang=EN-US><font face=Arial>/</font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">析构</span><span lang=EN-US><font face=Arial>/</font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">赋值运算</span><span lang=EN-US><font face=Arial>(</font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">之一</span><span lang=EN-US><font face=Arial>)</font></span></font></font></h2>
<h3 style="MARGIN: 13pt 0cm"><font size=5><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">条款</span><span lang=EN-US>05</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：了解</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">默默编写并调用哪些函数</span></font></h3>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">如果你自己没声明，编译器就会为类声明一个</span><span lang=EN-US>copy</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数、一个</span><span lang=EN-US>copy assignment</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">操作符和一个析构函数。此外如果你没声明任何构造函数，编译器也会为你声明一个</span><span lang=EN-US>default</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数。</span><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 15pt; COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">只有当这些函数被需要（被调用），它们才被编译器创建出来。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 15pt; COLOR: blue"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">注意：</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">编译器产出的析构函数是</span><span lang=EN-US>non-virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的，除非这个</span><span lang=EN-US>class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的</span><span lang=EN-US>base class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">声明有</span><span lang=EN-US>virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">析构函数。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">编译器何时拒绝生出</span><span lang=EN-US style="COLOR: red">operator=</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">？</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">一般而言只有当生出的代码合法且有适当机会证明它有意义，编译器生成的</span><span lang=EN-US>copy assignment</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">操作符其行为与</span><span lang=EN-US>copy</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数如出一辙。万一两个条件有一个不符合，编译器就拒绝为</span><span lang=EN-US>class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">生产</span><span lang=EN-US>operator=</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span><span style="COLOR: fuchsia; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">情况</span><span lang=EN-US style="COLOR: fuchsia">1</span><span style="COLOR: fuchsia; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">当类含</span><span lang=EN-US>reference</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员时，编译器将拒绝为其生成</span><span lang=EN-US>copy assignment</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">操作符。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span><span style="COLOR: fuchsia; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">情况</span><span lang=EN-US style="COLOR: fuchsia">2</span><span style="COLOR: fuchsia; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">当类含</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员时，编译器将拒绝为其生成</span><span lang=EN-US>copy assignment</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">操作符。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span><span style="COLOR: fuchsia; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">情况</span><span lang=EN-US style="COLOR: fuchsia">3</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：如果某类的</span><span lang=EN-US>base classes</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">将</span><span lang=EN-US>copy assignment</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">操作符声明为</span><span lang=EN-US>private</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，编译器将拒绝为其</span><span lang=EN-US>derived classes</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">生成</span><span lang=EN-US>copy assignment</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">操作符。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">【要点摘录】</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">不允许&#8220;让</span><span lang=EN-US>referenct</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">改指向不同的对象&#8221;。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">请记住：</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">编译器可以暗自为</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">class</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">创建</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">default</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数、</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">copy</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数、</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">copy assignment</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">操作符，以及析构函数。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<img src ="http://www.cppblog.com/yugong/aggbug/37357.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/yugong/" target="_blank">Nathan.Yu</a> 2007-11-27 00:52 <a href="http://www.cppblog.com/yugong/articles/37357.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Effective C++读书笔记—1 让自己习惯C++(之3)</title><link>http://www.cppblog.com/yugong/articles/37356.html</link><dc:creator>Nathan.Yu</dc:creator><author>Nathan.Yu</author><pubDate>Mon, 26 Nov 2007 16:51:00 GMT</pubDate><guid>http://www.cppblog.com/yugong/articles/37356.html</guid><wfw:comment>http://www.cppblog.com/yugong/comments/37356.html</wfw:comment><comments>http://www.cppblog.com/yugong/articles/37356.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/yugong/comments/commentRss/37356.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/yugong/services/trackbacks/37356.html</trackback:ping><description><![CDATA[<h1 style="MARGIN: 17pt 0cm 16.5pt; TEXT-ALIGN: center" align=center><font size=6><font color=#000000><span lang=EN-US><font face="Times New Roman">Effective C++</font></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">读书笔记</span></font></font></h1>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 210pt; TEXT-INDENT: 21pt"><em style="mso-bidi-font-style: normal"><span lang=EN-US style="FONT-SIZE: 14pt">--By Nathan.Yu 2007-11-12--<o:p></o:p></span></em></p>
<h2 style="MARGIN: 13pt 0cm"><font size=5><font color=#000000><span lang=EN-US><font face=Arial>1 </font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">让自己习惯</span><span lang=EN-US><font face=Arial>C++(</font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">三</span><span lang=EN-US><font face=Arial>)</font></span></font></font></h2>
<h3 style="MARGIN: 13pt 0cm"><font size=5><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">条款</span><span lang=EN-US>04</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：确定对象被使用前已先被初始化</span></font></h3>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">读取未初始化的值会导致不明确的行为。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">最佳的处理方法：永远在使用对象之前先将它初始化。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对内置类型：手工初始化。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对自定义类型：确保每个构造函数都将对象的每一个成员初始化。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">别混淆了赋值（</span><span lang=EN-US>assignment</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）和初始化（</span><span lang=EN-US>initialization</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt; TEXT-INDENT: -18pt; mso-list: l0 level1 lfo1; tab-stops: list 18.0pt"><span lang=EN-US style="COLOR: red; mso-fareast-font-family: 'Times New Roman'"><span style="mso-list: Ignore">1、<span style="FONT: 7pt 'Times New Roman'">&nbsp; </span></span></span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员初始化何时发生？</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt"><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">规定，对象的成员变量的初始化发生在进入构造函数本体之前。使用</span><span lang=EN-US>member initialization list</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">（成员初值列表）替换在构造函数体中的赋值动作。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt; TEXT-INDENT: -18pt; mso-list: l0 level1 lfo1; tab-stops: list 18.0pt"><span lang=EN-US style="COLOR: red; mso-fareast-font-family: 'Times New Roman'"><span style="mso-list: Ignore">2、<span style="FONT: 7pt 'Times New Roman'">&nbsp; </span></span></span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">为什么使用初始化列表效率较高？</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">初始化列表避免了先调用成员的</span><span lang=EN-US>default</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数这一多余的过程。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt; TEXT-INDENT: -18pt; mso-list: l0 level1 lfo1; tab-stops: list 18.0pt"><span lang=EN-US style="mso-fareast-font-family: 'Times New Roman'"><span style="mso-list: Ignore">3、<span style="FONT: 7pt 'Times New Roman'">&nbsp; </span></span></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">内置类型成员应选用初始化列表还是赋值进行初始化？</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">内置类型的&#8220;赋值表现像初始化一样好&#8221;，但为了一致，最好也通过成员初始列表来初始化内置类型。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">【要点摘录】请立下规则：规定总是在初值列表中列出所有成员变量，以免还得记得哪些成员变量（如果它们在初值列表中被遗漏的话）可以无需初值。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt; TEXT-INDENT: -18pt; mso-list: l0 level1 lfo1; tab-stops: list 18.0pt"><span lang=EN-US style="COLOR: red; mso-fareast-font-family: 'Times New Roman'"><span style="mso-list: Ignore">4、<span style="FONT: 7pt 'Times New Roman'">&nbsp; </span></span></span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">何时内置类型成员变量必须使用初值列表初始化？</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">当它们是</span><span lang=EN-US style="COLOR: blue">const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">或</span><span lang=EN-US style="COLOR: blue">references</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">时，它们就一定需要初值，不能被赋值。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt; TEXT-INDENT: -18pt; mso-list: l0 level1 lfo1; tab-stops: list 18.0pt"><span lang=EN-US style="COLOR: red; mso-fareast-font-family: 'Times New Roman'"><span style="mso-list: Ignore">5、<span style="FONT: 7pt 'Times New Roman'">&nbsp; </span></span></span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">有多个构造函数，且成员较多时怎么办？如何初始化？</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">在这种情况下，可以合理的在初值列表中遗漏那些&#8220;赋值表现像初始化一样好&#8221;对成员，改用它们的赋值操作，并将那些赋值操作移往某个函数（通常是</span><span lang=EN-US>private</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">），共所有构造函数调用。这种做法在&#8220;成员变量的初值系由文件或数据库读入&#8221;时特别有用。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt; TEXT-INDENT: -18pt; mso-list: l0 level1 lfo1; tab-stops: list 18.0pt"><span lang=EN-US style="COLOR: red; mso-fareast-font-family: 'Times New Roman'"><span style="mso-list: Ignore">6、<span style="FONT: 7pt 'Times New Roman'">&nbsp; </span></span></span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员的初始化顺序如何</span><span lang=EN-US style="COLOR: red">?<o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt"><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">有十分固定的初始化次序：</span><span lang=EN-US>base classes</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">更早于其</span><span lang=EN-US>derived classes</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">被初始化，而</span><span lang=EN-US>classes</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">当成员变量总是以其声明的次序初始化。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">【要点摘录】为避免你或你的检阅者迷惑，并避免某些可能存在的晦涩的错误，当你在初始化列表中以声明的次序初始化各成员。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt; TEXT-INDENT: -18pt; mso-list: l0 level1 lfo1; tab-stops: list 18.0pt"><span lang=EN-US style="COLOR: red; mso-fareast-font-family: 'Times New Roman'"><span style="mso-list: Ignore">7、<span style="FONT: 7pt 'Times New Roman'">&nbsp; </span></span></span><span lang=EN-US style="COLOR: red">static</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象有哪些？</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">所谓</span><span lang=EN-US>static</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象，其寿命从被构造出来直到程序结束为止，因此</span><span lang=EN-US>stack</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">和</span><span lang=EN-US>heap</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象都被排除。这种对象包括：</span><span lang=EN-US>global</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象；定义于</span><span lang=EN-US>namespace</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">作用域内的对象；在</span><span lang=EN-US>classes</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">内、在函数内、以及在</span><span lang=EN-US>file</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">作用域内被声明为</span><span lang=EN-US>static</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的对象。其中，函数中的</span><span lang=EN-US>static</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象称为</span><span lang=EN-US>local static</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象，其他</span><span lang=EN-US>static</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象称为</span><span lang=EN-US>non-local static</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象。</span><span lang=EN-US>static</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象的析构函数会在</span><span lang=EN-US>main</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数结束时被自动调用。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt; TEXT-INDENT: -18pt; mso-list: l0 level1 lfo1; tab-stops: list 18.0pt"><span lang=EN-US style="COLOR: red; mso-fareast-font-family: 'Times New Roman'"><span style="mso-list: Ignore">8、<span style="FONT: 7pt 'Times New Roman'">&nbsp; </span></span></span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">什么是编译单元？</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">所谓编译单元</span><span lang=EN-US>(translation unit)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，是指产出单一目标文件的那些源码。基本上它是单一源码文件加上其所含入的头文件。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 18pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">【要点摘录】</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对&#8220;定义于不同编译单元内的</span><span lang=EN-US>non-local static</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象&#8221;的初始化次序并无明确定义。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt; TEXT-INDENT: 18pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">【要点摘录】</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">保证，函数内的</span><span lang=EN-US>local static</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象在&#8220;该函数被调用期间&#8221;&#8220;首次遇上该对象之定义式&#8221;时被初始化。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">请记住：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">1</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、为内置型对象进行手工初始化，因为</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">C++</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">不保证初始化它们。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">2</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、构造函数最好使用成员初值列表，而不要在构造函数体内使用赋值操作。初值列表列出的成员变量，其排列次序该和它们在</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">class</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">中的声明次序相同。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">3</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、为免除&#8220;跨编译单元之初始化次序&#8221;问题，请以</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">local static</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象替换</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">non-local static </span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象。（使用</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">reference-returning</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数）。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<img src ="http://www.cppblog.com/yugong/aggbug/37356.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/yugong/" target="_blank">Nathan.Yu</a> 2007-11-27 00:51 <a href="http://www.cppblog.com/yugong/articles/37356.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Effective C++读书笔记—1 让自己习惯C++(之2)</title><link>http://www.cppblog.com/yugong/articles/37355.html</link><dc:creator>Nathan.Yu</dc:creator><author>Nathan.Yu</author><pubDate>Mon, 26 Nov 2007 16:50:00 GMT</pubDate><guid>http://www.cppblog.com/yugong/articles/37355.html</guid><wfw:comment>http://www.cppblog.com/yugong/comments/37355.html</wfw:comment><comments>http://www.cppblog.com/yugong/articles/37355.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/yugong/comments/commentRss/37355.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/yugong/services/trackbacks/37355.html</trackback:ping><description><![CDATA[<h1 style="MARGIN: 17pt 0cm 16.5pt; TEXT-ALIGN: center" align=center><font size=6><font color=#000000><span lang=EN-US><font face="Times New Roman">Effective C++</font></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">读书笔记</span></font></font></h1>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 210pt; TEXT-INDENT: 21pt"><em style="mso-bidi-font-style: normal"><span lang=EN-US style="FONT-SIZE: 14pt">--By Nathan.Yu 2007-11-11--<o:p></o:p></span></em></p>
<h2 style="MARGIN: 13pt 0cm"><font size=5><font color=#000000><span lang=EN-US><font face=Arial>1 </font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">让自己习惯</span><span lang=EN-US><font face=Arial>C++(</font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">二</span><span lang=EN-US><font face=Arial>)</font></span></font></font></h2>
<h3 style="MARGIN: 13pt 0cm"><font size=5><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">条款</span><span lang=EN-US>03</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：尽可能使用</span><span lang=EN-US>const</span></font></h3>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">允许你指定一个语义约束（也就是指定一个&#8220;不该被改动&#8221;的对象），而编译器会强制实施这项约束。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: red">const</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的用处</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：<span style="COLOR: green">修饰</span></span><span lang=EN-US style="COLOR: green">global</span><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">或</span><span lang=EN-US style="COLOR: green">namespace</span><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">作用域中的常量；或修饰文件、函数、或区块作用域中被声明为</span><span lang=EN-US style="COLOR: green">static</span><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的对象；也可以修饰</span><span lang=EN-US style="COLOR: green">classes</span><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">内的</span><span lang=EN-US style="COLOR: green">static</span><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">和</span><span lang=EN-US style="COLOR: green">non-static</span><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员变量；修饰指针（迭代器）及它们所指定对象等。而最具威力的用法是在函数声明中，在一个函数声明内，</span><span lang=EN-US style="COLOR: green">const</span><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">可以和函数返回值、参数、函数自身（成员函数）产生关联。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">与指针：如果关键字</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">出现在星号左边（类型之前或之后一样），表示被指物是常量；如果出现在星号右边，表示指针本身是常量；如果出现在星号两边，表示被指物和指针都是常量。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">与迭代器：声明迭代器为</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">（即</span><span lang=EN-US>const ..::iterator x</span><span lang=EN-US style="FONT-FAMILY: Wingdings; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'; mso-char-type: symbol; mso-symbol-font-family: Wingdings"><span style="mso-char-type: symbol; mso-symbol-font-family: Wingdings">&#243;</span></span><span lang=EN-US>T* const x</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）表示这个迭代器不能指向不同的东西，但它指向的东西是可以改动的。如果希望迭代器所指定东西不可被改动</span><span lang=EN-US>,</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">可使用</span><span lang=EN-US>const_iterator;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">【要点摘录】一个&#8220;良好的用户自定义类型&#8221;的特征是它们避免无端的与内置类型不兼容。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员函数：将</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">实施与成员函数的目的，是为了确认该成员函数可作用于</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象（当然也可作用于非</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象），而非</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员函数则只能作用与非</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员函数使&#8220;操作</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象&#8221;成为可能，这对编写高效代码是个关键。因为改善</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">程序效率的一个根本方法是以</span><span lang=EN-US>pass-by-referenct-to-const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">方式传递对象，而此技术可行的前提是我们有</span><span lang=EN-US style="COLOR: red">const</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员函数</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">可用来<span style="COLOR: red">处理</span>取得（并经修饰而成）的</span><span lang=EN-US style="COLOR: red">const</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>&lt;</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">在普通的非</span><span lang=EN-US style="COLOR: blue">const</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员函数中，</span><span lang=EN-US style="COLOR: blue">this</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">指针的类型是</span><span lang=EN-US style="COLOR: green">T* const this</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的，可以改变所指物，但不能改变指针本身；在</span><span lang=EN-US style="COLOR: blue">const</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员函数中，</span><span lang=EN-US style="COLOR: blue">this</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">指针的类型是</span><span lang=EN-US style="COLOR: green">const T* const this</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的，二者都不能改变</span><span lang=EN-US>&gt;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">【要点摘录】两个成员函数如果只是常量性不同，可以被重载。这实在是一个重要的</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">特性。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">【要点摘录】如果函数的返回类型是个内置类型，那么改动函数返回值从来就是不合法的。如：</span><span lang=EN-US>int f(); f()=1;</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">是不合法的！</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">关于</span><span lang=EN-US style="COLOR: red">const</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员函数的两个学派：</span><span lang=EN-US>bitwise constness(</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">又称</span><span lang=EN-US>physical constness)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">和</span><span lang=EN-US>logical constness</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: red">mutable</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">（可变的）关键字</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：释放掉</span><span lang=EN-US>non-static</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员变量的</span><span lang=EN-US>bitwise constness</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">约束，使在成员函数中可修改</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员的值。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">在</span><span lang=EN-US style="COLOR: red">const</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">和</span><span lang=EN-US style="COLOR: red">non-const</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员函数中避免重复：</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">允许</span><span lang=EN-US>non-const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">调用</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，而不允许</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">调用</span><span lang=EN-US>non-const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。因为</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员函数调用</span><span lang=EN-US>non-const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员函数时，对象有可能被改动。</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">调用</span><span lang=EN-US>non-const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">时，必须用</span><span lang=EN-US>const_cast</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">将</span><span lang=EN-US>*this</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">上的</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">性质去掉才能调用，这是不安全的做法。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">请记住：</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">1</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、将某些东西声明为</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">const</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">可帮助编译器侦测出错误用法。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">const</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">可被施加于任何作用域内的对象、函数参数、函数返回类型、成员函数本体。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">2</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、编译器强制实施</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">bitwise constness</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，但你编写程序时应该使用&#8220;概念上的常量性&#8221;（</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">conceptual constness</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">3</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、当</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">const</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">和</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">non-const</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员函数有着实质等价的实现时，令</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">non-const</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">版本调用</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">const</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">版本可避免代码重复。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<img src ="http://www.cppblog.com/yugong/aggbug/37355.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/yugong/" target="_blank">Nathan.Yu</a> 2007-11-27 00:50 <a href="http://www.cppblog.com/yugong/articles/37355.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Effective C++读书笔记—1 让自己习惯C++(之1)</title><link>http://www.cppblog.com/yugong/articles/37354.html</link><dc:creator>Nathan.Yu</dc:creator><author>Nathan.Yu</author><pubDate>Mon, 26 Nov 2007 16:49:00 GMT</pubDate><guid>http://www.cppblog.com/yugong/articles/37354.html</guid><wfw:comment>http://www.cppblog.com/yugong/comments/37354.html</wfw:comment><comments>http://www.cppblog.com/yugong/articles/37354.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/yugong/comments/commentRss/37354.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/yugong/services/trackbacks/37354.html</trackback:ping><description><![CDATA[<h1 style="MARGIN: 17pt 0cm 16.5pt; TEXT-ALIGN: center" align=center><font size=6><font color=#000000><span lang=EN-US><font face="Times New Roman">Effective C++</font></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">读书笔记</span></font></font></h1>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 210pt; TEXT-INDENT: 21pt"><em style="mso-bidi-font-style: normal"><span lang=EN-US style="FONT-SIZE: 14pt">--By Nathan.Yu 2007-11-10--<o:p></o:p></span></em></p>
<h2 style="MARGIN: 13pt 0cm"><font size=5><font color=#000000><span lang=EN-US><font face=Arial>1 </font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">让自己习惯</span><span lang=EN-US><font face=Arial>C++</font></span></font></font></h2>
<h3 style="MARGIN: 13pt 0cm"><font size=5><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">条款</span><span lang=EN-US>01</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：视</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">为一个语言联邦</span></font></h3>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">最初的名称是：</span><span lang=EN-US>C with Classes</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">今天的</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">是：多重泛型编程语言</span><span lang=EN-US>(multiparadigm programming language)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，同时支持过程形式（</span><span lang=EN-US>procedural</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）、面向对象形式（</span><span lang=EN-US>object-oriented</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）、函数形式（</span><span lang=EN-US>functional</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）、泛型形式（</span><span lang=EN-US>generic</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）、元编程形式（</span><span lang=EN-US>metaprogramming</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）的语言。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">将</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">视为一个由相关语言组成的联邦而非单一语言。在某个次语言（</span><span lang=EN-US>sublanguage</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）中，各种守则与通例都倾向简单、直观易懂、并且容易记住。然而当从一个次语言移往另一个次语言，守则可能改变。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">认识</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">主要的次语言：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>C</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">以</span><span lang=EN-US>C</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">为基础。区块（</span><span lang=EN-US>blocks</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）、语句（</span><span lang=EN-US>statements</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）、预处理（</span><span lang=EN-US>preprocessor</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）、内置数据类型（</span><span lang=EN-US>built-in data types</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）、数组（</span><span lang=EN-US>arrays</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）、指针（</span><span lang=EN-US>pointers</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）等都来自</span><span lang=EN-US>C</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>C</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的局限：没有模板（</span><span lang=EN-US>templates</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）、没有异常（</span><span lang=EN-US>exceptions</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）、没有重载（</span><span lang=EN-US>overloading</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）</span><span lang=EN-US>&#8230;&#8230;.</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><st1:place w:st="on"><span lang=EN-US>Ob</span></st1:place><span lang=EN-US>ject-Oriented C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：</span><span lang=EN-US>classes(</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">包括构造函数和析构函数</span><span lang=EN-US>)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、封装（</span><span lang=EN-US>encapsulation</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）、继承（</span><span lang=EN-US>inheritance</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）、多态（</span><span lang=EN-US>polymorphism</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）、</span><span lang=EN-US>virtual</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数（动态绑定）</span><span lang=EN-US>&#8230;&#8230;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">是面向对象设计之古典守则在</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">上的最直接实施。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>Template C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：即</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的泛型编程（</span><span lang=EN-US>generic programming</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）部分。由于</span><span lang=EN-US>templates</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的强大威力，带来了崭新的编程泛型，即所谓的模板元编程（</span><span lang=EN-US>template metaprogramming</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，</span><span lang=EN-US>TMP</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>STL</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：是一个</span><span lang=EN-US>template</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">程序库。</span><span lang=EN-US>STL</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">有自己特殊的办事方式，当你伙同</span><span lang=EN-US>STL</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">一起工作，必须遵守它的规约。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">当你从一个次语言切换到另一个时，相应的高效编程守则要求你改变策略，以参数传递方式为例：对内置类型而言</span><span lang=EN-US>pass-by-value</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">通常比</span><span lang=EN-US>pass-by-reference</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">高效，但当你从</span><span lang=EN-US>C part of C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">移往</span><span lang=EN-US>Object-Oriented C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，由于用户自定义构造函数和析构函数的存在，</span><span lang=EN-US>pass-by-reference-to-const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">往往更好。运用</span><span lang=EN-US>Template C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">时更是如此，因为彼时你甚至不知道所处理的对象的类型。然而在</span><span lang=EN-US>STL</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">中，迭代器和函数对象都是在</span><span lang=EN-US>c</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">指针之上塑造出来的，所以对</span><span lang=EN-US>STL</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">迭代器和函数对象而言，</span><span lang=EN-US>pass-by-value</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">再次适用（仅仅指迭代器和函数对象）。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">请记住</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">C++</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">高效编程守则视状况而变化，取决于你使用</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">C++</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的哪一部分。</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple"><o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<h3 style="MARGIN: 13pt 0cm"><font size=5><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">条款</span><span lang=EN-US>02</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：尽量以</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，</span><span lang=EN-US>enum</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，</span><span lang=EN-US>inline</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">替换</span><span lang=EN-US>#define</span></font></h3>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">&#8220;宁以编译器替换预处理器&#8221;，因为或许</span><span lang=EN-US>#define</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">不被视为语言的一部分。当你：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>#define ASPECT_RATIO 1.653</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">记号名</span><span lang=EN-US>ASPECT_RATIO</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">也许从没被编译器看见；也许在编译器开始处理源代码之前它就被预处理器移走了。于是记号</span><span lang=EN-US>ASPECT_RATIO</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">有可能没有进入记号表（</span><span lang=EN-US>symbol table</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）内。因此不能用此记号来获得编译错误信息。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">解决之道：用一个常量替换宏（</span><span lang=EN-US>#define</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">），</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>const double AspectRatio = 1.653;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">常量定义通常放在头文件内，以便不同的源码含入。因此有必要将指针（而不是指针所指之物）声明为</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: red">const</span><span lang=EN-US>/*</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">需要吗？</span><span lang=EN-US>*/ <span style="COLOR: blue">char*</span> <span style="COLOR: red">const</span>/*</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">防止在不同的地方改变</span><span lang=EN-US>authorName </span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的指向吧</span><span lang=EN-US>?!*/<span style="COLOR: red"> </span><span style="COLOR: blue">authorName = &#8220;Scott Meyers&#8221;;<o:p></o:p></span></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: blue"><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>Class </span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">专属常量：为了将常量的作用域</span><span lang=EN-US>(scope)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">限制于</span><span lang=EN-US>class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">内，你必须让它成为</span><span lang=EN-US>class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">第一个成员</span><span lang=EN-US>(member)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">；而为确保此常量至多只有一份实体，必须让它成为一个</span><span lang=EN-US>static</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>class GamePlayer{</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>private:</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span><span style="COLOR: red">static const int NumTurns = 5;</span><span style="mso-spacerun: yes">&nbsp; </span><span style="COLOR: blue">//</span></span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">常量声明式，注意是声明！！！！！不是定义</span><span lang=EN-US style="COLOR: blue"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: blue">/*<o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">通常</span><span lang=EN-US style="COLOR: blue">C++</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">要求你对所使用的任何东西提供一个定义式，但如果它是个</span><span lang=EN-US style="COLOR: blue">class</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">专属常量，又是</span><span lang=EN-US style="COLOR: blue">static</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，又是整数类型（</span><span lang=EN-US style="COLOR: blue">ints</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、</span><span lang=EN-US style="COLOR: blue">chars</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、</span><span lang=EN-US style="COLOR: blue">bools</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">），则可特殊处理：即只要不取他们的地址，可以只声明而不定义便可使用。但如果你取某个</span><span lang=EN-US style="COLOR: blue">class</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">专属常量的地址，或你使用的编译器（不标准的）坚持要一个定义式，则必须提供定义式如下：</span><span lang=EN-US style="COLOR: blue"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: red">const int GamePlayer::NumTurns; //</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">没有赋值，因为声明式已经为其设立初值</span><span lang=EN-US style="COLOR: red">5</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，故此略去</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><u><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">注意：这个定义式应放进</span><span lang=EN-US style="COLOR: green">class</span></u><u><span style="COLOR: green; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的实现文件，而非头文件。</span><span lang=EN-US style="COLOR: green"><o:p></o:p></span></u></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: blue">*/<o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>int scores[NumTurns]; //</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">常量的使用</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>};</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">（无法用</span><span lang=EN-US>#define</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">创建一个</span><span lang=EN-US>class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">专属常量！更别提像</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员那样可以被封装了！）</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">旧时的编译器也许不支持上述语法：它们不允许</span><span lang=EN-US>static</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">成员在声明式上获得初值。此外&#8220;</span><span lang=EN-US>in-class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">初值设定&#8221;也只允许对整数常量进行。若此，则可：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>class CostEstimate{</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>private:</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span><span style="COLOR: red">static const double FudgeFactor;</span><span style="COLOR: blue">//</span></span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">声明，位于头文件</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>&#8230;&#8230;.</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>};</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: red">const double CostEstimate:: FudgeFactor = 1.35</span><span lang=EN-US style="COLOR: blue">;//</span><span style="COLOR: blue; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">定义，位于实现文件</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">此外，可改用&#8220;</span><span lang=EN-US>the enum hack</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">&#8221;补偿做法。其理论基础是：&#8220;一个属于枚举类型的数值可权充</span><span lang=EN-US>ints</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">被使用&#8221;，于是：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>class GamePlayer{</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>private:</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span><span style="COLOR: red">enum { NumTurns = 5};<o:p></o:p></span></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><span style="mso-tab-count: 1">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; </span>int scores[NumTurns];</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>};</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>enum hack</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的行为像</span><span lang=EN-US>define</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">而不像</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，例如，取一个</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的地址是合法的，而取</span><span lang=EN-US>enum</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">和</span><span lang=EN-US>define</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对地址都是不合法的。虽然，优秀的编译器不会为&#8220;整数型</span><span lang=EN-US>const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象&#8221;设定另外的存储空间（除非你创建了一个</span><span lang=EN-US>pointer</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">或</span><span lang=EN-US>reference</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">指向该对象），不够优秀的编译器却可能如此，而这可能不是你想要的。</span><span lang=EN-US>Enums</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">和</span><span lang=EN-US>#defines</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">一样绝不会导致非必要的内存分配。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">另外，</span><span lang=EN-US>enum hack</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">还是</span><span lang=EN-US>TMP</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对基础技术。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>template inline</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数：可以获得宏带来的效率以及一般函数的所有可预料行为和类型安全。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">请记住：</span><span lang=EN-US style="COLOR: red"><o:p></o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">1</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、对于单纯常量，最好以</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">const</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对象或</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">enums</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">替换</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">#defines<o:p></o:p></span></strong></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">2</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、对于形似函数的宏，最好改用</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">inline</span></strong><strong style="mso-bidi-font-weight: normal"><span style="FONT-SIZE: 14pt; COLOR: purple; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数替换</span></strong><strong style="mso-bidi-font-weight: normal"><span lang=EN-US style="FONT-SIZE: 14pt; COLOR: purple">#defines<o:p></o:p></span></strong></p>
<img src ="http://www.cppblog.com/yugong/aggbug/37354.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/yugong/" target="_blank">Nathan.Yu</a> 2007-11-27 00:49 <a href="http://www.cppblog.com/yugong/articles/37354.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Effective C++读书笔记—0 导读</title><link>http://www.cppblog.com/yugong/articles/37353.html</link><dc:creator>Nathan.Yu</dc:creator><author>Nathan.Yu</author><pubDate>Mon, 26 Nov 2007 16:47:00 GMT</pubDate><guid>http://www.cppblog.com/yugong/articles/37353.html</guid><wfw:comment>http://www.cppblog.com/yugong/comments/37353.html</wfw:comment><comments>http://www.cppblog.com/yugong/articles/37353.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/yugong/comments/commentRss/37353.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/yugong/services/trackbacks/37353.html</trackback:ping><description><![CDATA[<h1 style="MARGIN: 17pt 0cm 16.5pt; TEXT-ALIGN: center" align=center><font size=6><font color=#000000><span lang=EN-US><font face="Times New Roman">Effective C++</font></span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">读书笔记</span></font></font></h1>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt 210pt; TEXT-INDENT: 21pt"><em style="mso-bidi-font-style: normal"><span lang=EN-US style="FONT-SIZE: 14pt">--By Nathan.Yu 2007-11-10--<o:p></o:p></span></em></p>
<h2 style="MARGIN: 13pt 0cm"><font size=5><font color=#000000><span lang=EN-US><font face=Arial>0 </font></span><span style="FONT-FAMILY: 黑体; mso-ascii-font-family: Arial">导读</span></font></font></h2>
<h3 style="MARGIN: 13pt 0cm"><font size=5><span lang=EN-US>1</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、设计策略</span></font></h3>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">如何在两个不同的做法中择一完成某项任务，如</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">该选择</span><span lang=EN-US>inheritance(</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">继承</span><span lang=EN-US>)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">还是</span><span lang=EN-US>templates</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">（模板）？该选择</span><span lang=EN-US>public</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">继承还是</span><span lang=EN-US>private</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">继承？该选择</span><span lang=EN-US>private</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">继承还是</span><span lang=EN-US>composition</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">（复合）？该选择</span><span lang=EN-US>member</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数还是</span><span lang=EN-US>non-member</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数？该选择</span><span lang=EN-US>pass-by-value</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">还是</span><span lang=EN-US>pass-by-reference</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">？</span><span lang=EN-US>&#8230;. </span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">什么是</span><span lang=EN-US>assignment</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">操作符的适当返回类型</span><span lang=EN-US>?</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">何时该令析构函数为</span><span lang=EN-US>virtual?</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">当</span><span lang=EN-US>operator new</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">无法找到足够的内存时该如何行事？</span><span lang=EN-US>&#8230;..</span></p>
<h3 style="MARGIN: 13pt 0cm"><font size=5><span lang=EN-US>2</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、术语</span></font></h3>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">声明式（</span><span lang=EN-US style="COLOR: red">declaration</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：告诉编译器某个东西的名称和类型，但略去细节。如</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>extern int x;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>std::size_t numDigits(int number);</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>/*</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>std::size_t,</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">表示类型</span><span lang=EN-US>size_t</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">位于命名空间</span><span lang=EN-US>std</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">内。而继承自</span><span lang=EN-US>c</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">动符号（如</span><span lang=EN-US>size_t</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）有可能存在于</span><span lang=EN-US>global</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">作用域或</span><span lang=EN-US>std</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">内，甚至两个兼具，取决于哪个头文件被含入</span><span lang=EN-US>(#included).</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">每个函数的声明揭示其签名式</span><span lang=EN-US>(signature)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，也就是参数类型和返回类型。如，</span><span lang=EN-US>numDigits</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数的签名是</span><span lang=EN-US>std::size_t (int)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。但</span><span lang=EN-US>c++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对签名的官方定义并不包含返回类型。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>*/</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>class Widget;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>template&lt;typename T&gt; class GraphNode;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">定义式</span><span lang=EN-US style="COLOR: red">(definition)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：告诉编译器声明式所遗漏的细节。对对象而言，定义式是编译器对此对象拨发内存的地点；对</span><span lang=EN-US>function</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">或</span><span lang=EN-US>function template</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">而言，定义式提供了代码本体；对</span><span lang=EN-US>class</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">或</span><span lang=EN-US>class template</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">而言，定义式列出它们的成员。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">初始化</span><span lang=EN-US style="COLOR: red">(Initialization)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：&#8220;给予对象初值&#8221;的过程。对用户自定义的类型的对象而言，初始化由构造函数执行。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: red">default</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：是一个可被调用而不带任何实参的类成员函数。这样的构造函数要不没有参数，要不就是每个参数都有缺省值。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: red">explicit</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：可以阻止它们被用来执行隐式类型转换</span><span lang=EN-US>(implicit type conversions)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，但可显式转换</span><span lang=EN-US>(explicit type conversions)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。被声明为</span><span lang=EN-US>explicit</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">第构造函数通常比其</span><span lang=EN-US>non-explicit</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">兄弟更受欢迎，因为他禁止编译器执行预期（往往是不期望）的类型转换。把构造函数声明为</span><span lang=EN-US>explicit</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">！</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: red">copy</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：以同型对象初始化新自我对象。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>copy assignment</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">操作符：从一个同型对象中拷贝其值到另一个自我对象。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: red">pass-by-value</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：意味&#8220;调用</span><span lang=EN-US>copy</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">构造函数&#8221;。以</span><span lang=EN-US>by-value</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">传递用户自定义类型通常是个坏主意，</span><span lang=EN-US>pass-by-reference-to-const</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">往往是比较好的选择。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: red">STL</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：标准模板库</span><span lang=EN-US>(Standard Template Library)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，包含容器（如</span><span lang=EN-US>vector</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，</span><span lang=EN-US> list</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，</span><span lang=EN-US> set</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，</span><span lang=EN-US> map</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">等等）、迭代器（如</span><span lang=EN-US>vector&lt;int&gt;::iterator, set&lt;string&gt;::const_iterator</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">等等）、算法（如</span><span lang=EN-US>for_each</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，</span><span lang=EN-US> find</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">，</span><span lang=EN-US> sort</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">等等）机能。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">函数对象（</span><span lang=EN-US style="COLOR: red">function objects</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：行为像函数的对象，这样的对象来自于重载</span><span lang=EN-US>operator()(function call </span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">操作符</span><span lang=EN-US>)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的</span><span lang=EN-US>classes</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">行为没有定义</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：你无法稳定预估运行期会发生什么事。如</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>int* p = 0;</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>std::cout &lt;&lt; *p; //</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">对一个</span><span lang=EN-US>null</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">指针取值会导致不明确行为。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">接口（</span><span lang=EN-US style="COLOR: red">interface</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：</span><span lang=EN-US>Java</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">和</span><span lang=EN-US>.NET</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">语言都提供</span><span lang=EN-US>Interfaces</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">为语言元素，但</span><span lang=EN-US>c++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">没有。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US><o:p>&nbsp;</o:p></span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">客户（</span><span lang=EN-US style="COLOR: red">client</span><span style="COLOR: red; FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：某人或某物，他</span><span lang=EN-US>(</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">或它</span><span lang=EN-US>)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">使用你的代码（通常是一些接口）。一般指程序员。</span></p>
<h3 style="MARGIN: 13pt 0cm"><font size=5><span lang=EN-US>3</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">、</span><span lang=EN-US>TR1</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">和</span><span lang=EN-US>Boost</span></font></h3>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: red">TR1(Technical Report 1)</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">：一份规范，描述加入</span><span lang=EN-US>C++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">标准程序库的诸多新机能。这些机能以新的</span><span lang=EN-US>class templates </span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">和</span><span lang=EN-US> function templates</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">形式体现，有</span><span lang=EN-US>hash tables, reference-counting smart pointers, regular expressions</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">等，所有</span><span lang=EN-US>TR1</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">组件都被置于命名空间</span><span lang=EN-US>tr1</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">中，</span><span lang=EN-US>tr1</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">则位于</span><span lang=EN-US>std</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">内（即</span><span lang=EN-US>std::tr1</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">）。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US style="COLOR: red">Boost</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">是个组织，提供可移植、同僚复审、源码开放的</span><span lang=EN-US>c++</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">程序库。大多数</span><span lang=EN-US>TR1</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">机能是以</span><span lang=EN-US>Boost</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的工作为基础的。</span><span lang=EN-US>Boost</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">提供比</span><span lang=EN-US>TR1</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">更多的东西。</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt"><span lang=EN-US>TR1</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">与</span><span lang=EN-US>Boost</span><span style="FONT-FAMILY: 宋体; mso-ascii-font-family: 'Times New Roman'; mso-hansi-font-family: 'Times New Roman'">的关系：</span></p>
<p class=MsoNormal style="MARGIN: 0cm 0cm 0pt; TEXT-ALIGN: center" align=center><br><img height=117 alt="" src="http://www.cppblog.com/images/cppblog_com/yugong/tr1_boost.JPG" width=243 border=0><span lang=EN-US></span><span lang=EN-US><o:p></o:p></span></p>
<img src ="http://www.cppblog.com/yugong/aggbug/37353.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/yugong/" target="_blank">Nathan.Yu</a> 2007-11-27 00:47 <a href="http://www.cppblog.com/yugong/articles/37353.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item></channel></rss>