﻿<?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++博客-创的技术博客-随笔分类-C\C++</title><link>http://www.cppblog.com/converse/category/803.html</link><description>C++对我而言就是有STL带class能处理多态,继承的C.</description><language>zh-cn</language><lastBuildDate>Mon, 19 May 2008 21:04:21 GMT</lastBuildDate><pubDate>Mon, 19 May 2008 21:04:21 GMT</pubDate><ttl>60</ttl><item><title>研究了一下SGI STL的内存算法</title><link>http://www.cppblog.com/converse/archive/2008/04/01/45947.html</link><dc:creator>创</dc:creator><author>创</author><pubDate>Tue, 01 Apr 2008 11:55:00 GMT</pubDate><guid>http://www.cppblog.com/converse/archive/2008/04/01/45947.html</guid><wfw:comment>http://www.cppblog.com/converse/comments/45947.html</wfw:comment><comments>http://www.cppblog.com/converse/archive/2008/04/01/45947.html#Feedback</comments><slash:comments>6</slash:comments><wfw:commentRss>http://www.cppblog.com/converse/comments/commentRss/45947.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/converse/services/trackbacks/45947.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: 仿SGI STL的内存池算法.<br>&nbsp;&nbsp;<a href='http://www.cppblog.com/converse/archive/2008/04/01/45947.html'>阅读全文</a><img src ="http://www.cppblog.com/converse/aggbug/45947.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/converse/" target="_blank">创</a> 2008-04-01 19:55 <a href="http://www.cppblog.com/converse/archive/2008/04/01/45947.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>memcache内存池的设计原理</title><link>http://www.cppblog.com/converse/archive/2008/01/21/41592.html</link><dc:creator>创</dc:creator><author>创</author><pubDate>Mon, 21 Jan 2008 15:34:00 GMT</pubDate><guid>http://www.cppblog.com/converse/archive/2008/01/21/41592.html</guid><wfw:comment>http://www.cppblog.com/converse/comments/41592.html</wfw:comment><comments>http://www.cppblog.com/converse/archive/2008/01/21/41592.html#Feedback</comments><slash:comments>1</slash:comments><wfw:commentRss>http://www.cppblog.com/converse/comments/commentRss/41592.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/converse/services/trackbacks/41592.html</trackback:ping><description><![CDATA[memcache中管理内存的数据结构如下:<br><br>
<div style="BORDER-RIGHT: #cccccc 1px solid; PADDING-RIGHT: 5px; BORDER-TOP: #cccccc 1px solid; PADDING-LEFT: 4px; FONT-SIZE: 13px; PADDING-BOTTOM: 4px; BORDER-LEFT: #cccccc 1px solid; WIDTH: 98%; WORD-BREAK: break-all; PADDING-TOP: 4px; BORDER-BOTTOM: #cccccc 1px solid; BACKGROUND-COLOR: #eeeeee"><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top><span style="COLOR: #000000">typedef&nbsp;struct&nbsp;{<br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;unsigned&nbsp;</span><span style="COLOR: #0000ff">int</span><span style="COLOR: #000000">&nbsp;size;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="COLOR: #000000">/*</span><span style="COLOR: #000000">&nbsp;sizes&nbsp;of&nbsp;items&nbsp;</span><span style="COLOR: #000000">*/</span><span style="COLOR: #000000"><br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;unsigned&nbsp;</span><span style="COLOR: #0000ff">int</span><span style="COLOR: #000000">&nbsp;perslab;&nbsp;&nbsp;&nbsp;</span><span style="COLOR: #000000">/*</span><span style="COLOR: #000000">&nbsp;how&nbsp;many&nbsp;items&nbsp;per&nbsp;slab&nbsp;</span><span style="COLOR: #000000">*/</span><span style="COLOR: #000000"><br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top><br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;void&nbsp;</span><span style="COLOR: #000000">**</span><span style="COLOR: #000000">slots;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="COLOR: #000000">/*</span><span style="COLOR: #000000">&nbsp;list&nbsp;of&nbsp;item&nbsp;ptrs&nbsp;</span><span style="COLOR: #000000">*/</span><span style="COLOR: #000000"><br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;unsigned&nbsp;</span><span style="COLOR: #0000ff">int</span><span style="COLOR: #000000">&nbsp;sl_total;&nbsp;&nbsp;</span><span style="COLOR: #000000">/*</span><span style="COLOR: #000000">&nbsp;size&nbsp;of&nbsp;previous&nbsp;</span><span style="COLOR: #0000ff">array</span><span style="COLOR: #000000">&nbsp;</span><span style="COLOR: #000000">*/</span><span style="COLOR: #000000"><br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;unsigned&nbsp;</span><span style="COLOR: #0000ff">int</span><span style="COLOR: #000000">&nbsp;sl_curr;&nbsp;&nbsp;&nbsp;</span><span style="COLOR: #000000">/*</span><span style="COLOR: #000000">&nbsp;first&nbsp;free&nbsp;slot&nbsp;</span><span style="COLOR: #000000">*/</span><span style="COLOR: #000000"><br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top><br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;void&nbsp;</span><span style="COLOR: #000000">*</span><span style="COLOR: #000000">end_page_ptr;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="COLOR: #000000">/*</span><span style="COLOR: #000000">&nbsp;pointer&nbsp;</span><span style="COLOR: #0000ff">to</span><span style="COLOR: #000000">&nbsp;</span><span style="COLOR: #0000ff">next</span><span style="COLOR: #000000">&nbsp;free&nbsp;item&nbsp;at&nbsp;</span><span style="COLOR: #0000ff">end</span><span style="COLOR: #000000">&nbsp;of&nbsp;page,&nbsp;</span><span style="COLOR: #0000ff">or</span><span style="COLOR: #000000">&nbsp;</span><span style="COLOR: #000000">0</span><span style="COLOR: #000000">&nbsp;</span><span style="COLOR: #000000">*/</span><span style="COLOR: #000000"><br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;unsigned&nbsp;</span><span style="COLOR: #0000ff">int</span><span style="COLOR: #000000">&nbsp;end_page_free;&nbsp;</span><span style="COLOR: #000000">/*</span><span style="COLOR: #000000">&nbsp;number&nbsp;of&nbsp;items&nbsp;remaining&nbsp;at&nbsp;</span><span style="COLOR: #0000ff">end</span><span style="COLOR: #000000">&nbsp;of&nbsp;last&nbsp;alloced&nbsp;page&nbsp;</span><span style="COLOR: #000000">*/</span><span style="COLOR: #000000"><br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top><br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;unsigned&nbsp;</span><span style="COLOR: #0000ff">int</span><span style="COLOR: #000000">&nbsp;slabs;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="COLOR: #000000">/*</span><span style="COLOR: #000000">&nbsp;how&nbsp;many&nbsp;slabs&nbsp;were&nbsp;allocated&nbsp;</span><span style="COLOR: #0000ff">for</span><span style="COLOR: #000000">&nbsp;this&nbsp;class&nbsp;</span><span style="COLOR: #000000">*/</span><span style="COLOR: #000000"><br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top><br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;void&nbsp;</span><span style="COLOR: #000000">**</span><span style="COLOR: #000000">slab_list;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="COLOR: #000000">/*</span><span style="COLOR: #000000">&nbsp;</span><span style="COLOR: #0000ff">array</span><span style="COLOR: #000000">&nbsp;of&nbsp;slab&nbsp;pointers&nbsp;</span><span style="COLOR: #000000">*/</span><span style="COLOR: #000000"><br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;unsigned&nbsp;</span><span style="COLOR: #0000ff">int</span><span style="COLOR: #000000">&nbsp;list_size;&nbsp;</span><span style="COLOR: #000000">/*</span><span style="COLOR: #000000">&nbsp;size&nbsp;of&nbsp;prev&nbsp;</span><span style="COLOR: #0000ff">array</span><span style="COLOR: #000000">&nbsp;</span><span style="COLOR: #000000">*/</span><span style="COLOR: #000000"><br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top><br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;unsigned&nbsp;</span><span style="COLOR: #0000ff">int</span><span style="COLOR: #000000">&nbsp;killing;&nbsp;&nbsp;</span><span style="COLOR: #000000">/*</span><span style="COLOR: #000000">&nbsp;index</span><span style="COLOR: #000000">+</span><span style="COLOR: #000000">1</span><span style="COLOR: #000000">&nbsp;of&nbsp;dying&nbsp;slab,&nbsp;</span><span style="COLOR: #0000ff">or</span><span style="COLOR: #000000">&nbsp;zero&nbsp;</span><span style="COLOR: #0000ff">if</span><span style="COLOR: #000000">&nbsp;none&nbsp;</span><span style="COLOR: #000000">*/</span><span style="COLOR: #000000"><br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top>}&nbsp;slabclass_t;<br><img src="http://www.cppblog.com/Images/OutliningIndicators/None.gif" align=top></span></div>
<br>程序中有一个全局的数组<br>static slabclass_t slabclass[POWER_LARGEST + 1]用于保存slab,预分配内存池时调用的是void slabs_init(const size_t limit, const double factor) 函数,其中limit是内存池的最大容量,factor是分配时的增长因子.<br>比方说,加入factor是2,第一个在slabclass数组中的slab的每个item大小是128字节,那么下一个slab每个item的大小就是128*2,再下一个就是128*2*2(注意,为了简化问题的说明,上面没有考虑地址对齐的因素).<br><br>在预分配内存池时,最多给每个slab保存item的容量是1M内存,这个数值由#define POWER_BLOCK 1048576决定.<br>因此,slab中的几个元素在预分配内存时是这么定的:<br>size有一个起始值,这个值以后的增长由factor决定,增长的过程前面已经阐述过了;<br>perslab保存的是一个slab存放的item数量,因此perslab = POWER_BLOCK / slabclass[i].size;<br>如果预先分配一段内存供使用的话,也就是没有定义DONT_PREALLOC_SLABS宏,那么就调用slabs_preallocate进行预分配内存.<br>其中,end_page_ptr指向这个预分配好的指针,end_page_free表示的是目前空闲可用item的数量,在预分配时,这个值与perslab相同.<br>在这个内存池模型中,每个page实际上是一个数组,数组中每个元素的大小就是这个slab中item的大小.<br><br>另外,slots保存的是释放出来的item指针,sl_total表示总的数量,sl_curr表示的是目前可用的已经释放出来的item数量.<br><br>每一次要分配内存的时候,首先根据需要分配的内存大小在slabclass数组中查找索引最小的一个大于所要求内存的slab,如果slots不为空,那么就从这里返回内存,否则去查找end_page_ptr,如果也没有,那么就只能返回NULL了.<br>每一次释放内存的时候,同样的找到应该返回内存的slab元素,改写前面提到的slot指针和sl_curr数.<br><br>有点仓促,以后再完善~~<br><br><br>
<img src ="http://www.cppblog.com/converse/aggbug/41592.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/converse/" target="_blank">创</a> 2008-01-21 23:34 <a href="http://www.cppblog.com/converse/archive/2008/01/21/41592.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>仿STL中的堆算法的一个实现</title><link>http://www.cppblog.com/converse/archive/2007/03/20/20175.html</link><dc:creator>创</dc:creator><author>创</author><pubDate>Mon, 19 Mar 2007 16:28:00 GMT</pubDate><guid>http://www.cppblog.com/converse/archive/2007/03/20/20175.html</guid><wfw:comment>http://www.cppblog.com/converse/comments/20175.html</wfw:comment><comments>http://www.cppblog.com/converse/archive/2007/03/20/20175.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/converse/comments/commentRss/20175.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/converse/services/trackbacks/20175.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: 仿STL中的堆算法的一个实现&nbsp;&nbsp;<a href='http://www.cppblog.com/converse/archive/2007/03/20/20175.html'>阅读全文</a><img src ="http://www.cppblog.com/converse/aggbug/20175.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/converse/" target="_blank">创</a> 2007-03-20 00:28 <a href="http://www.cppblog.com/converse/archive/2007/03/20/20175.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>CGL开发手记之一--参考资料</title><link>http://www.cppblog.com/converse/archive/2007/03/18/20083.html</link><dc:creator>创</dc:creator><author>创</author><pubDate>Sun, 18 Mar 2007 11:40:00 GMT</pubDate><guid>http://www.cppblog.com/converse/archive/2007/03/18/20083.html</guid><wfw:comment>http://www.cppblog.com/converse/comments/20083.html</wfw:comment><comments>http://www.cppblog.com/converse/archive/2007/03/18/20083.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/converse/comments/commentRss/20083.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/converse/services/trackbacks/20083.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: 有关CGL写作中经常参考到的资料.&nbsp;&nbsp;<a href='http://www.cppblog.com/converse/archive/2007/03/18/20083.html'>阅读全文</a><img src ="http://www.cppblog.com/converse/aggbug/20083.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/converse/" target="_blank">创</a> 2007-03-18 19:40 <a href="http://www.cppblog.com/converse/archive/2007/03/18/20083.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Modern C++ Design(MCD)学习笔记 &amp;&amp; 测试代码(二)</title><link>http://www.cppblog.com/converse/archive/2007/02/04/18340.html</link><dc:creator>创</dc:creator><author>创</author><pubDate>Sun, 04 Feb 2007 15:18:00 GMT</pubDate><guid>http://www.cppblog.com/converse/archive/2007/02/04/18340.html</guid><wfw:comment>http://www.cppblog.com/converse/comments/18340.html</wfw:comment><comments>http://www.cppblog.com/converse/archive/2007/02/04/18340.html#Feedback</comments><slash:comments>5</slash:comments><wfw:commentRss>http://www.cppblog.com/converse/comments/commentRss/18340.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/converse/services/trackbacks/18340.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: 检查是否可以转换以及是否存在继承关系的类<br>&nbsp;&nbsp;<a href='http://www.cppblog.com/converse/archive/2007/02/04/18340.html'>阅读全文</a><img src ="http://www.cppblog.com/converse/aggbug/18340.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/converse/" target="_blank">创</a> 2007-02-04 23:18 <a href="http://www.cppblog.com/converse/archive/2007/02/04/18340.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Modern C++ Design(MCD)学习笔记 &amp;&amp; 测试代码(一)</title><link>http://www.cppblog.com/converse/archive/2007/02/04/18325.html</link><dc:creator>创</dc:creator><author>创</author><pubDate>Sun, 04 Feb 2007 07:53:00 GMT</pubDate><guid>http://www.cppblog.com/converse/archive/2007/02/04/18325.html</guid><wfw:comment>http://www.cppblog.com/converse/comments/18325.html</wfw:comment><comments>http://www.cppblog.com/converse/archive/2007/02/04/18325.html#Feedback</comments><slash:comments>1</slash:comments><wfw:commentRss>http://www.cppblog.com/converse/comments/commentRss/18325.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/converse/services/trackbacks/18325.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: 编译期断言模版类的技巧~~&nbsp;&nbsp;<a href='http://www.cppblog.com/converse/archive/2007/02/04/18325.html'>阅读全文</a><img src ="http://www.cppblog.com/converse/aggbug/18325.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/converse/" target="_blank">创</a> 2007-02-04 15:53 <a href="http://www.cppblog.com/converse/archive/2007/02/04/18325.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>little endian和big endian的概念解释,判定与用途</title><link>http://www.cppblog.com/converse/archive/2006/09/05/12058.html</link><dc:creator>创</dc:creator><author>创</author><pubDate>Tue, 05 Sep 2006 13:04:00 GMT</pubDate><guid>http://www.cppblog.com/converse/archive/2006/09/05/12058.html</guid><wfw:comment>http://www.cppblog.com/converse/comments/12058.html</wfw:comment><comments>http://www.cppblog.com/converse/archive/2006/09/05/12058.html#Feedback</comments><slash:comments>3</slash:comments><wfw:commentRss>http://www.cppblog.com/converse/comments/commentRss/12058.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/converse/services/trackbacks/12058.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: little endian和big endian的概念解释,判定与用途&nbsp;&nbsp;<a href='http://www.cppblog.com/converse/archive/2006/09/05/12058.html'>阅读全文</a><img src ="http://www.cppblog.com/converse/aggbug/12058.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/converse/" target="_blank">创</a> 2006-09-05 21:04 <a href="http://www.cppblog.com/converse/archive/2006/09/05/12058.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>测试了一下VC和gcc对关键字export的支持</title><link>http://www.cppblog.com/converse/archive/2006/07/11/9695.html</link><dc:creator>创</dc:creator><author>创</author><pubDate>Tue, 11 Jul 2006 11:04:00 GMT</pubDate><guid>http://www.cppblog.com/converse/archive/2006/07/11/9695.html</guid><wfw:comment>http://www.cppblog.com/converse/comments/9695.html</wfw:comment><comments>http://www.cppblog.com/converse/archive/2006/07/11/9695.html#Feedback</comments><slash:comments>11</slash:comments><wfw:commentRss>http://www.cppblog.com/converse/comments/commentRss/9695.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/converse/services/trackbacks/9695.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: 测试了一下VC和gcc对关键字export的支持&nbsp;&nbsp;<a href='http://www.cppblog.com/converse/archive/2006/07/11/9695.html'>阅读全文</a><img src ="http://www.cppblog.com/converse/aggbug/9695.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/converse/" target="_blank">创</a> 2006-07-11 19:04 <a href="http://www.cppblog.com/converse/archive/2006/07/11/9695.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>探索C++的秘密之二:重载,覆盖,和隐藏   </title><link>http://www.cppblog.com/converse/archive/2006/03/24/4564.html</link><dc:creator>创</dc:creator><author>创</author><pubDate>Fri, 24 Mar 2006 12:39:00 GMT</pubDate><guid>http://www.cppblog.com/converse/archive/2006/03/24/4564.html</guid><wfw:comment>http://www.cppblog.com/converse/comments/4564.html</wfw:comment><comments>http://www.cppblog.com/converse/archive/2006/03/24/4564.html#Feedback</comments><slash:comments>3</slash:comments><wfw:commentRss>http://www.cppblog.com/converse/comments/commentRss/4564.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/converse/services/trackbacks/4564.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: 三个概念重载,覆盖,和隐藏的区别.&nbsp;&nbsp;<a href='http://www.cppblog.com/converse/archive/2006/03/24/4564.html'>阅读全文</a><img src ="http://www.cppblog.com/converse/aggbug/4564.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/converse/" target="_blank">创</a> 2006-03-24 20:39 <a href="http://www.cppblog.com/converse/archive/2006/03/24/4564.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>使用typename的一个说明</title><link>http://www.cppblog.com/converse/archive/2006/03/22/4476.html</link><dc:creator>创</dc:creator><author>创</author><pubDate>Wed, 22 Mar 2006 15:41:00 GMT</pubDate><guid>http://www.cppblog.com/converse/archive/2006/03/22/4476.html</guid><wfw:comment>http://www.cppblog.com/converse/comments/4476.html</wfw:comment><comments>http://www.cppblog.com/converse/archive/2006/03/22/4476.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/converse/comments/commentRss/4476.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/converse/services/trackbacks/4476.html</trackback:ping><description><![CDATA[时常看到这样的代码,比如以下这两段代码:<br /><div style="BORDER-RIGHT: #cccccc 1px solid; PADDING-RIGHT: 5px; BORDER-TOP: #cccccc 1px solid; PADDING-LEFT: 4px; FONT-SIZE: 13px; PADDING-BOTTOM: 4px; BORDER-LEFT: #cccccc 1px solid; WIDTH: 98%; WORD-BREAK: break-all; PADDING-TOP: 4px; BORDER-BOTTOM: #cccccc 1px solid; BACKGROUND-COLOR: #eeeeee"><img src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align="top" /><span style="COLOR: #000000">list</span><span style="COLOR: #000000">&lt;</span><span style="COLOR: #0000ff">int</span><span style="COLOR: #000000">&gt;</span><span style="COLOR: #000000">::iterator iter1;<br /><img src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align="top" />list</span><span style="COLOR: #000000">&lt;</span><span style="COLOR: #000000">T</span><span style="COLOR: #000000">&gt;</span><span style="COLOR: #000000">::iterator iter1;</span></div><br />前者没有问题可以顺利的编译过去，但是后者时常会报一个警告，为什么呢?<br />原因如下:<br />首先,list&lt;T&gt;是一个模板类，在模板实例化以前是无法确定起真正的类型的,也就是说编译阶段是无法知道到底是哪个类的,那么可能出现以下一种情况：某个类中恰好有一个静态成员为iterator，此时就会出错了。<br />因此为了明确的指出这是一个类型而不是一个成员，我们需要在前面加上typename，也就是:<br /><div style="BORDER-RIGHT: #cccccc 1px solid; PADDING-RIGHT: 5px; BORDER-TOP: #cccccc 1px solid; PADDING-LEFT: 4px; FONT-SIZE: 13px; PADDING-BOTTOM: 4px; BORDER-LEFT: #cccccc 1px solid; WIDTH: 98%; WORD-BREAK: break-all; PADDING-TOP: 4px; BORDER-BOTTOM: #cccccc 1px solid; BACKGROUND-COLOR: #eeeeee"><img src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align="top" /><span style="COLOR: #000000">typename list</span><span style="COLOR: #000000">&lt;</span><span style="COLOR: #000000">T</span><span style="COLOR: #000000">&gt;</span><span style="COLOR: #000000">::iterator iter1;</span></div>typename在这里用于说明后面紧跟着的字符串表示的是一个类型。<img src ="http://www.cppblog.com/converse/aggbug/4476.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/converse/" target="_blank">创</a> 2006-03-22 23:41 <a href="http://www.cppblog.com/converse/archive/2006/03/22/4476.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>模板套模板～～</title><link>http://www.cppblog.com/converse/archive/2006/03/22/4445.html</link><dc:creator>创</dc:creator><author>创</author><pubDate>Tue, 21 Mar 2006 16:06:00 GMT</pubDate><guid>http://www.cppblog.com/converse/archive/2006/03/22/4445.html</guid><wfw:comment>http://www.cppblog.com/converse/comments/4445.html</wfw:comment><comments>http://www.cppblog.com/converse/archive/2006/03/22/4445.html#Feedback</comments><slash:comments>5</slash:comments><wfw:commentRss>http://www.cppblog.com/converse/comments/commentRss/4445.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/converse/services/trackbacks/4445.html</trackback:ping><description><![CDATA[
		<div style="BORDER-RIGHT: #cccccc 1px solid; PADDING-RIGHT: 5px; BORDER-TOP: #cccccc 1px solid; PADDING-LEFT: 4px; FONT-SIZE: 13px; PADDING-BOTTOM: 4px; BORDER-LEFT: #cccccc 1px solid; WIDTH: 98%; WORD-BREAK: break-all; PADDING-TOP: 4px; BORDER-BOTTOM: #cccccc 1px solid; BACKGROUND-COLOR: #eeeeee">
				<img src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align="top" />
				<span style="COLOR: #000000">#include </span>
				<span style="COLOR: #000000">&lt;</span>
				<span style="COLOR: #000000">iostream</span>
				<span style="COLOR: #000000">&gt;</span>
				<span style="COLOR: #000000">
						<br />
						<img src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align="top" />#include </span>
				<span style="COLOR: #000000">&lt;</span>
				<span style="COLOR: #000000">map</span>
				<span style="COLOR: #000000">&gt;</span>
				<span style="COLOR: #000000">
						<br />
						<img src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align="top" />#include </span>
				<span style="COLOR: #000000">&lt;</span>
				<span style="COLOR: #0000ff">string</span>
				<span style="COLOR: #000000">&gt;</span>
				<span style="COLOR: #000000">
						<br />
						<img src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align="top" />
						<br />
						<img src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align="top" />
				</span>
				<span style="COLOR: #0000ff">using</span>
				<span style="COLOR: #000000"> </span>
				<span style="COLOR: #0000ff">namespace</span>
				<span style="COLOR: #000000"> std;<br /><img src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align="top" /><br /><img src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align="top" /></span>
				<span style="COLOR: #0000ff">int</span>
				<span style="COLOR: #000000"> main()<br /><img id="Codehighlighter1_87_263_Open_Image" onclick="this.style.display='none'; Codehighlighter1_87_263_Open_Text.style.display='none'; Codehighlighter1_87_263_Closed_Image.style.display='inline'; Codehighlighter1_87_263_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockStart.gif" align="top" /><img id="Codehighlighter1_87_263_Closed_Image" style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_87_263_Closed_Text.style.display='none'; Codehighlighter1_87_263_Open_Image.style.display='inline'; Codehighlighter1_87_263_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedBlock.gif" align="top" /></span>
				<span id="Codehighlighter1_87_263_Closed_Text" style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff">
						<img src="http://www.cppblog.com/images/dot.gif" />
				</span>
				<span id="Codehighlighter1_87_263_Open_Text">
						<span style="COLOR: #000000">{<br /><img src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align="top" />    map</span>
						<span style="COLOR: #000000">&lt;</span>
						<span style="COLOR: #0000ff">string</span>
						<span style="COLOR: #000000">, </span>
						<span style="COLOR: #0000ff">int</span>
						<span style="COLOR: #000000">&gt;</span>
						<span style="COLOR: #000000"> map1;<br /><img src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align="top" />    map</span>
						<span style="COLOR: #000000">&lt;</span>
						<span style="COLOR: #0000ff">string</span>
						<span style="COLOR: #000000">, map</span>
						<span style="COLOR: #000000">&lt;</span>
						<span style="COLOR: #0000ff">string</span>
						<span style="COLOR: #000000">, </span>
						<span style="COLOR: #0000ff">int</span>
						<span style="COLOR: #000000">&gt;</span>
						<span style="COLOR: #000000"> </span>
						<span style="COLOR: #000000">&gt;</span>
						<span style="COLOR: #000000"> map2;<br /><img src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align="top" />    map1[</span>
						<span style="COLOR: #000000">"</span>
						<span style="COLOR: #000000">test</span>
						<span style="COLOR: #000000">"</span>
						<span style="COLOR: #000000">] </span>
						<span style="COLOR: #000000">=</span>
						<span style="COLOR: #000000"> </span>
						<span style="COLOR: #000000">2</span>
						<span style="COLOR: #000000">;<br /><img src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align="top" />    map2[</span>
						<span style="COLOR: #000000">"</span>
						<span style="COLOR: #000000">test1</span>
						<span style="COLOR: #000000">"</span>
						<span style="COLOR: #000000">] </span>
						<span style="COLOR: #000000">=</span>
						<span style="COLOR: #000000"> map1;<br /><img src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align="top" /><br /><img src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align="top" />    cout </span>
						<span style="COLOR: #000000">&lt;&lt;</span>
						<span style="COLOR: #000000"> map2[</span>
						<span style="COLOR: #000000">"</span>
						<span style="COLOR: #000000">test1</span>
						<span style="COLOR: #000000">"</span>
						<span style="COLOR: #000000">][</span>
						<span style="COLOR: #000000">"</span>
						<span style="COLOR: #000000">test</span>
						<span style="COLOR: #000000">"</span>
						<span style="COLOR: #000000">] </span>
						<span style="COLOR: #000000">&lt;&lt;</span>
						<span style="COLOR: #000000"> endl;<br /><img src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align="top" />    </span>
						<span style="COLOR: #0000ff">return</span>
						<span style="COLOR: #000000"> </span>
						<span style="COLOR: #000000">0</span>
						<span style="COLOR: #000000">;<br /><img src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockEnd.gif" align="top" />}</span>
				</span>
		</div>以上代码简单的实现了map对"二维"形式的支持,很简单,不是么？可是我第一次面对这个问题的时候模板套模板的整糊涂了,记录一个留个念想～～<img src ="http://www.cppblog.com/converse/aggbug/4445.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/converse/" target="_blank">创</a> 2006-03-22 00:06 <a href="http://www.cppblog.com/converse/archive/2006/03/22/4445.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>一个关于临时对象和虚拟析构函数的问题</title><link>http://www.cppblog.com/converse/archive/2006/02/16/3297.html</link><dc:creator>创</dc:creator><author>创</author><pubDate>Thu, 16 Feb 2006 15:24:00 GMT</pubDate><guid>http://www.cppblog.com/converse/archive/2006/02/16/3297.html</guid><wfw:comment>http://www.cppblog.com/converse/comments/3297.html</wfw:comment><comments>http://www.cppblog.com/converse/archive/2006/02/16/3297.html#Feedback</comments><slash:comments>2</slash:comments><wfw:commentRss>http://www.cppblog.com/converse/comments/commentRss/3297.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/converse/services/trackbacks/3297.html</trackback:ping><description><![CDATA[在CU逛,别人问到这样的一个问题,大致如下:<BR><BR><FONT size=2><FONT color=#0000ff>
<DIV style="BORDER-RIGHT: #cccccc 1px solid; PADDING-RIGHT: 5px; BORDER-TOP: #cccccc 1px solid; PADDING-LEFT: 4px; FONT-SIZE: 13px; PADDING-BOTTOM: 4px; BORDER-LEFT: #cccccc 1px solid; WIDTH: 98%; WORD-BREAK: break-all; PADDING-TOP: 4px; BORDER-BOTTOM: #cccccc 1px solid; BACKGROUND-COLOR: #eeeeee"><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top><SPAN style="COLOR: #000000">#include&nbsp;</SPAN><SPAN style="COLOR: #000000">&lt;</SPAN><SPAN style="COLOR: #000000">iostream</SPAN><SPAN style="COLOR: #000000">&gt;</SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>#include&nbsp;</SPAN><SPAN style="COLOR: #000000">&lt;</SPAN><SPAN style="COLOR: #0000ff">string</SPAN><SPAN style="COLOR: #000000">&gt;</SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">using</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #0000ff">namespace</SPAN><SPAN style="COLOR: #000000">&nbsp;std;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">class</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #0000ff">base</SPAN><SPAN style="COLOR: #000000"><BR><IMG id=Codehighlighter1_70_210_Open_Image onclick="this.style.display='none'; Codehighlighter1_70_210_Open_Text.style.display='none'; Codehighlighter1_70_210_Closed_Image.style.display='inline'; Codehighlighter1_70_210_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockStart.gif" align=top><IMG id=Codehighlighter1_70_210_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_70_210_Closed_Text.style.display='none'; Codehighlighter1_70_210_Open_Image.style.display='inline'; Codehighlighter1_70_210_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedBlock.gif" align=top></SPAN><SPAN id=Codehighlighter1_70_210_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_70_210_Open_Text><SPAN style="COLOR: #000000">{<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">public</SPAN><SPAN style="COLOR: #000000">:<BR><IMG id=Codehighlighter1_124_153_Open_Image onclick="this.style.display='none'; Codehighlighter1_124_153_Open_Text.style.display='none'; Codehighlighter1_124_153_Closed_Image.style.display='inline'; Codehighlighter1_124_153_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedSubBlockStart.gif" align=top><IMG id=Codehighlighter1_124_153_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_124_153_Closed_Text.style.display='none'; Codehighlighter1_124_153_Open_Image.style.display='inline'; Codehighlighter1_124_153_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedSubBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">virtual</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #0000ff">void</SPAN><SPAN style="COLOR: #000000">&nbsp;print()</SPAN><SPAN id=Codehighlighter1_124_153_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_124_153_Open_Text><SPAN style="COLOR: #000000">{cout</SPAN><SPAN style="COLOR: #000000">&lt;&lt;</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">base::print()</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">&lt;&lt;</SPAN><SPAN style="COLOR: #000000">endl;}</SPAN></SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000">virtual&nbsp;~base(){}</SPAN><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000">增加虚析构函数，将导致输出不一致。</SPAN><SPAN style="COLOR: #008000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockEnd.gif" align=top></SPAN><SPAN style="COLOR: #000000">}</SPAN></SPAN><SPAN style="COLOR: #000000">;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">class</SPAN><SPAN style="COLOR: #000000">&nbsp;derived&nbsp;:</SPAN><SPAN style="COLOR: #0000ff">public</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #0000ff">base</SPAN><SPAN style="COLOR: #000000"><BR><IMG id=Codehighlighter1_240_329_Open_Image onclick="this.style.display='none'; Codehighlighter1_240_329_Open_Text.style.display='none'; Codehighlighter1_240_329_Closed_Image.style.display='inline'; Codehighlighter1_240_329_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockStart.gif" align=top><IMG id=Codehighlighter1_240_329_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_240_329_Closed_Text.style.display='none'; Codehighlighter1_240_329_Open_Image.style.display='inline'; Codehighlighter1_240_329_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedBlock.gif" align=top></SPAN><SPAN id=Codehighlighter1_240_329_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_240_329_Open_Text><SPAN style="COLOR: #000000">{<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">public</SPAN><SPAN style="COLOR: #000000">:<BR><IMG id=Codehighlighter1_294_327_Open_Image onclick="this.style.display='none'; Codehighlighter1_294_327_Open_Text.style.display='none'; Codehighlighter1_294_327_Closed_Image.style.display='inline'; Codehighlighter1_294_327_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedSubBlockStart.gif" align=top><IMG id=Codehighlighter1_294_327_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_294_327_Closed_Text.style.display='none'; Codehighlighter1_294_327_Open_Image.style.display='inline'; Codehighlighter1_294_327_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedSubBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">virtual</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #0000ff">void</SPAN><SPAN style="COLOR: #000000">&nbsp;print()</SPAN><SPAN id=Codehighlighter1_294_327_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_294_327_Open_Text><SPAN style="COLOR: #000000">{cout</SPAN><SPAN style="COLOR: #000000">&lt;&lt;</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">devrived::print()</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">&lt;&lt;</SPAN><SPAN style="COLOR: #000000">endl;}</SPAN></SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockEnd.gif" align=top>}</SPAN></SPAN><SPAN style="COLOR: #000000">;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">int</SPAN><SPAN style="COLOR: #000000">&nbsp;main(</SPAN><SPAN style="COLOR: #0000ff">int</SPAN><SPAN style="COLOR: #000000">&nbsp;argc,&nbsp;</SPAN><SPAN style="COLOR: #0000ff">char</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #000000">*</SPAN><SPAN style="COLOR: #000000">argv[])<BR><IMG id=Codehighlighter1_365_498_Open_Image onclick="this.style.display='none'; Codehighlighter1_365_498_Open_Text.style.display='none'; Codehighlighter1_365_498_Closed_Image.style.display='inline'; Codehighlighter1_365_498_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockStart.gif" align=top><IMG id=Codehighlighter1_365_498_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_365_498_Closed_Text.style.display='none'; Codehighlighter1_365_498_Open_Image.style.display='inline'; Codehighlighter1_365_498_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedBlock.gif" align=top></SPAN><SPAN id=Codehighlighter1_365_498_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_365_498_Open_Text><SPAN style="COLOR: #000000">{<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">base</SPAN><SPAN style="COLOR: #000000">*</SPAN><SPAN style="COLOR: #000000">&nbsp;p1</SPAN><SPAN style="COLOR: #000000">=&amp;</SPAN><SPAN style="COLOR: #000000">derived();<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;p1</SPAN><SPAN style="COLOR: #000000">-&gt;</SPAN><SPAN style="COLOR: #000000">print();<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;derived&nbsp;d;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">base</SPAN><SPAN style="COLOR: #000000">*</SPAN><SPAN style="COLOR: #000000">&nbsp;p2</SPAN><SPAN style="COLOR: #000000">=&amp;</SPAN><SPAN style="COLOR: #000000">d;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;p2</SPAN><SPAN style="COLOR: #000000">-&gt;</SPAN><SPAN style="COLOR: #000000">print();<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">return</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #000000">0</SPAN><SPAN style="COLOR: #000000">;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockEnd.gif" align=top>}</SPAN></SPAN></DIV><BR><BR></FONT>加入虚拟析构函数后，输出为：<BR>base::print()<BR>devrived::print()<BR>不加入虚拟析构函数，输出则为：<BR>devrived::print()<BR>devrived::print()</FONT><BR><BR><BR>我的解释如下:<BR><FONT size=2>实际上,第一个赋值指向的是一个临时对象,加入与没有加入虚拟析构函数的区别在于:加入之后,在derived类中会合成一个析构函数以便调用base的虚拟析构函数,如果没有加入的话那么就不会合成这个析构函数,所有的资源在main函数结束之后才回收.<BR><BR>因此,对于代码: base* p1=&amp;derived();<BR>没有加入虚拟析构函数的时候因为derived()函数生成的临时对象没有被销毁,因此对它的调用是对derived的调用;当加入虚拟析构函数之后,derived()函数生成的临时对象在以上的赋值完成之后就会调用析构函数进行析构,这个时候再次对p1调用print函数时,因为临时对象已经析构,那么这个调用就是对base的调用了.<BR><BR>我做了一个实验的代码,加了一些东西,大家看看~~<BR><BR></FONT>
<DIV class=smalltxt style="FONT-WEIGHT: bold; MARGIN-LEFT: 2em; MARGIN-RIGHT: 2em">
<DIV style="FLOAT: left"></DIV>
<DIV style="BORDER-RIGHT: #cccccc 1px solid; PADDING-RIGHT: 5px; BORDER-TOP: #cccccc 1px solid; PADDING-LEFT: 4px; FONT-SIZE: 13px; PADDING-BOTTOM: 4px; BORDER-LEFT: #cccccc 1px solid; WIDTH: 98%; WORD-BREAK: break-all; PADDING-TOP: 4px; BORDER-BOTTOM: #cccccc 1px solid; BACKGROUND-COLOR: #eeeeee"><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top><SPAN style="COLOR: #000000">#include&nbsp;</SPAN><SPAN style="COLOR: #000000">&lt;</SPAN><SPAN style="COLOR: #000000">iostream</SPAN><SPAN style="COLOR: #000000">&gt;</SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>#include&nbsp;</SPAN><SPAN style="COLOR: #000000">&lt;</SPAN><SPAN style="COLOR: #0000ff">string</SPAN><SPAN style="COLOR: #000000">&gt;</SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">using</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #0000ff">namespace</SPAN><SPAN style="COLOR: #000000">&nbsp;std;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">class</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #0000ff">base</SPAN><SPAN style="COLOR: #000000"><BR><IMG id=Codehighlighter1_70_229_Open_Image onclick="this.style.display='none'; Codehighlighter1_70_229_Open_Text.style.display='none'; Codehighlighter1_70_229_Closed_Image.style.display='inline'; Codehighlighter1_70_229_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockStart.gif" align=top><IMG id=Codehighlighter1_70_229_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_70_229_Closed_Text.style.display='none'; Codehighlighter1_70_229_Open_Image.style.display='inline'; Codehighlighter1_70_229_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedBlock.gif" align=top></SPAN><SPAN id=Codehighlighter1_70_229_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_70_229_Open_Text><SPAN style="COLOR: #000000">{<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">public</SPAN><SPAN style="COLOR: #000000">:<BR><IMG id=Codehighlighter1_124_153_Open_Image onclick="this.style.display='none'; Codehighlighter1_124_153_Open_Text.style.display='none'; Codehighlighter1_124_153_Closed_Image.style.display='inline'; Codehighlighter1_124_153_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedSubBlockStart.gif" align=top><IMG id=Codehighlighter1_124_153_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_124_153_Closed_Text.style.display='none'; Codehighlighter1_124_153_Open_Image.style.display='inline'; Codehighlighter1_124_153_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedSubBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">virtual</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #0000ff">void</SPAN><SPAN style="COLOR: #000000">&nbsp;print()</SPAN><SPAN id=Codehighlighter1_124_153_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_124_153_Open_Text><SPAN style="COLOR: #000000">{cout</SPAN><SPAN style="COLOR: #000000">&lt;&lt;</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">base::print()</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">&lt;&lt;</SPAN><SPAN style="COLOR: #000000">endl;}</SPAN></SPAN><SPAN style="COLOR: #000000"><BR><IMG id=Codehighlighter1_186_208_Open_Image onclick="this.style.display='none'; Codehighlighter1_186_208_Open_Text.style.display='none'; Codehighlighter1_186_208_Closed_Image.style.display='inline'; Codehighlighter1_186_208_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedSubBlockStart.gif" align=top><IMG id=Codehighlighter1_186_208_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_186_208_Closed_Text.style.display='none'; Codehighlighter1_186_208_Open_Image.style.display='inline'; Codehighlighter1_186_208_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedSubBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">virtual</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #000000">~</SPAN><SPAN style="COLOR: #0000ff">base</SPAN><SPAN style="COLOR: #000000">()</SPAN><SPAN id=Codehighlighter1_186_208_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_186_208_Open_Text><SPAN style="COLOR: #000000">{cout&nbsp;</SPAN><SPAN style="COLOR: #000000">&lt;&lt;</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">~base()\n</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">;}</SPAN></SPAN><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000">增加虚析构函数，将导致输出不一致。</SPAN><SPAN style="COLOR: #008000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockEnd.gif" align=top></SPAN><SPAN style="COLOR: #000000">}</SPAN></SPAN><SPAN style="COLOR: #000000">;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">class</SPAN><SPAN style="COLOR: #000000">&nbsp;derived&nbsp;:</SPAN><SPAN style="COLOR: #0000ff">public</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #0000ff">base</SPAN><SPAN style="COLOR: #000000"><BR><IMG id=Codehighlighter1_259_430_Open_Image onclick="this.style.display='none'; Codehighlighter1_259_430_Open_Text.style.display='none'; Codehighlighter1_259_430_Closed_Image.style.display='inline'; Codehighlighter1_259_430_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockStart.gif" align=top><IMG id=Codehighlighter1_259_430_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_259_430_Closed_Text.style.display='none'; Codehighlighter1_259_430_Open_Image.style.display='inline'; Codehighlighter1_259_430_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedBlock.gif" align=top></SPAN><SPAN id=Codehighlighter1_259_430_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_259_430_Open_Text><SPAN style="COLOR: #000000">{<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">public</SPAN><SPAN style="COLOR: #000000">:<BR><IMG id=Codehighlighter1_313_346_Open_Image onclick="this.style.display='none'; Codehighlighter1_313_346_Open_Text.style.display='none'; Codehighlighter1_313_346_Closed_Image.style.display='inline'; Codehighlighter1_313_346_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedSubBlockStart.gif" align=top><IMG id=Codehighlighter1_313_346_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_313_346_Closed_Text.style.display='none'; Codehighlighter1_313_346_Open_Image.style.display='inline'; Codehighlighter1_313_346_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedSubBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">virtual</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #0000ff">void</SPAN><SPAN style="COLOR: #000000">&nbsp;print()</SPAN><SPAN id=Codehighlighter1_313_346_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_313_346_Open_Text><SPAN style="COLOR: #000000">{cout</SPAN><SPAN style="COLOR: #000000">&lt;&lt;</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">devrived::print()</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">&lt;&lt;</SPAN><SPAN style="COLOR: #000000">endl;}</SPAN></SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000">virtual&nbsp;~derived(){cout&nbsp;&lt;&lt;&nbsp;"~derived()\n";}</SPAN><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000">增加虚析构函数，将导致输出不一致。</SPAN><SPAN style="COLOR: #008000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockEnd.gif" align=top></SPAN><SPAN style="COLOR: #000000">}</SPAN></SPAN><SPAN style="COLOR: #000000">;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">int</SPAN><SPAN style="COLOR: #000000">&nbsp;main(</SPAN><SPAN style="COLOR: #0000ff">int</SPAN><SPAN style="COLOR: #000000">&nbsp;argc,&nbsp;</SPAN><SPAN style="COLOR: #0000ff">char</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #000000">*</SPAN><SPAN style="COLOR: #000000">argv[])<BR><IMG id=Codehighlighter1_467_933_Open_Image onclick="this.style.display='none'; Codehighlighter1_467_933_Open_Text.style.display='none'; Codehighlighter1_467_933_Closed_Image.style.display='inline'; Codehighlighter1_467_933_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockStart.gif" align=top><IMG id=Codehighlighter1_467_933_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_467_933_Closed_Text.style.display='none'; Codehighlighter1_467_933_Open_Image.style.display='inline'; Codehighlighter1_467_933_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedBlock.gif" align=top></SPAN><SPAN id=Codehighlighter1_467_933_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_467_933_Open_Text><SPAN style="COLOR: #000000">{<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;derived&nbsp;</SPAN><SPAN style="COLOR: #000000">*</SPAN><SPAN style="COLOR: #000000">t&nbsp;</SPAN><SPAN style="COLOR: #000000">=</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #000000">&amp;</SPAN><SPAN style="COLOR: #000000">derived();<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">base</SPAN><SPAN style="COLOR: #000000">*</SPAN><SPAN style="COLOR: #000000">&nbsp;p1&nbsp;</SPAN><SPAN style="COLOR: #000000">=</SPAN><SPAN style="COLOR: #000000">&nbsp;t;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;p1</SPAN><SPAN style="COLOR: #000000">-&gt;</SPAN><SPAN style="COLOR: #000000">print();<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;derived&nbsp;d;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">base</SPAN><SPAN style="COLOR: #000000">*</SPAN><SPAN style="COLOR: #000000">&nbsp;p2</SPAN><SPAN style="COLOR: #000000">=&amp;</SPAN><SPAN style="COLOR: #000000">d;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;p2</SPAN><SPAN style="COLOR: #000000">-&gt;</SPAN><SPAN style="COLOR: #000000">print();<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000">&nbsp;第一部分相当于以下的代码<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000">&nbsp;用temp模拟临时对象</SPAN><SPAN style="COLOR: #008000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top></SPAN><SPAN style="COLOR: #000000">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;derived&nbsp;temp;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;derived&nbsp;</SPAN><SPAN style="COLOR: #000000">*</SPAN><SPAN style="COLOR: #000000">s&nbsp;</SPAN><SPAN style="COLOR: #000000">=</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #000000">&amp;</SPAN><SPAN style="COLOR: #000000">temp;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">base</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #000000">*</SPAN><SPAN style="COLOR: #000000">p3&nbsp;</SPAN><SPAN style="COLOR: #000000">=</SPAN><SPAN style="COLOR: #000000">&nbsp;s;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000">&nbsp;这次调用是对derived的函数调用</SPAN><SPAN style="COLOR: #008000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top></SPAN><SPAN style="COLOR: #000000">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;p3</SPAN><SPAN style="COLOR: #000000">-&gt;</SPAN><SPAN style="COLOR: #000000">print();<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000">&nbsp;显式地对temp进行析构</SPAN><SPAN style="COLOR: #008000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top></SPAN><SPAN style="COLOR: #000000">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;temp.</SPAN><SPAN style="COLOR: #0000ff">base</SPAN><SPAN style="COLOR: #000000">::</SPAN><SPAN style="COLOR: #000000">~</SPAN><SPAN style="COLOR: #0000ff">base</SPAN><SPAN style="COLOR: #000000">();<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000">&nbsp;析构完后,同样的一个内存,却是用base指针去解释,<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000">&nbsp;因此调用的是base的函数</SPAN><SPAN style="COLOR: #008000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top></SPAN><SPAN style="COLOR: #000000">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;p3</SPAN><SPAN style="COLOR: #000000">-&gt;</SPAN><SPAN style="COLOR: #000000">print();<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">return</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #000000">0</SPAN><SPAN style="COLOR: #000000">;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockEnd.gif" align=top>}</SPAN></SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN></DIV></DIV><img src ="http://www.cppblog.com/converse/aggbug/3297.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/converse/" target="_blank">创</a> 2006-02-16 23:24 <a href="http://www.cppblog.com/converse/archive/2006/02/16/3297.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>探索C++的秘密之一详解extern "C"</title><link>http://www.cppblog.com/converse/archive/2006/01/14/2733.html</link><dc:creator>创</dc:creator><author>创</author><pubDate>Sat, 14 Jan 2006 15:52:00 GMT</pubDate><guid>http://www.cppblog.com/converse/archive/2006/01/14/2733.html</guid><wfw:comment>http://www.cppblog.com/converse/comments/2733.html</wfw:comment><comments>http://www.cppblog.com/converse/archive/2006/01/14/2733.html#Feedback</comments><slash:comments>12</slash:comments><wfw:commentRss>http://www.cppblog.com/converse/comments/commentRss/2733.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/converse/services/trackbacks/2733.html</trackback:ping><description><![CDATA[<P>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 时常在cpp的代码之中看到这样的代码:<BR></P>
<DIV style="BORDER-RIGHT: #cccccc 1px solid; PADDING-RIGHT: 5px; BORDER-TOP: #cccccc 1px solid; PADDING-LEFT: 4px; FONT-SIZE: 13px; PADDING-BOTTOM: 4px; BORDER-LEFT: #cccccc 1px solid; WIDTH: 98%; WORD-BREAK: break-all; PADDING-TOP: 4px; BORDER-BOTTOM: #cccccc 1px solid; BACKGROUND-COLOR: #eeeeee"><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top><SPAN style="COLOR: #000000">#ifdef&nbsp;__cplusplus<BR><IMG id=Codehighlighter1_30_70_Open_Image onclick="this.style.display='none'; Codehighlighter1_30_70_Open_Text.style.display='none'; Codehighlighter1_30_70_Closed_Image.style.display='inline'; Codehighlighter1_30_70_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockStart.gif" align=top><IMG id=Codehighlighter1_30_70_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_30_70_Closed_Text.style.display='none'; Codehighlighter1_30_70_Open_Image.style.display='inline'; Codehighlighter1_30_70_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedBlock.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">extern</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">C</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN id=Codehighlighter1_30_70_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_30_70_Open_Text><SPAN style="COLOR: #000000">{<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">#endif</SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top></SPAN><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000"><IMG src="http://www.cppblog.com/images/dot.gif">一段代码</SPAN><SPAN style="COLOR: #008000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top></SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>#ifdef&nbsp;__cplusplus<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockEnd.gif" align=top>}</SPAN></SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">#endif</SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN></DIV>
<P><BR>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 这样的代码到底是什么意思呢?首先,__cplusplus是cpp中的自定义宏,那么定义了这个宏的话表示这是一段cpp的代码,也就是说,上面的代码的含义是:如果这是一段cpp的代码,那么加入extern "C"{和}处理其中的代码.</P>
<P>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 要明白为何使用extern "C",还得从cpp中对函数的重载处理开始说起.在c++中,为了支持重载机制,在编译生成的汇编码中,要对函数的名字进行一些处理,加入比如函数的返回类型等等.而在C中,只是简单的函数名字而已,不会加入其他的信息.也就是说:C++和C对产生的函数名字的处理是不一样的.</P>
<P>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 比如下面的一段简单的函数,我们看看加入和不加入extern "C"产生的汇编代码都有哪些变化:</P>
<DIV style="BORDER-RIGHT: #cccccc 1px solid; PADDING-RIGHT: 5px; BORDER-TOP: #cccccc 1px solid; PADDING-LEFT: 4px; FONT-SIZE: 13px; PADDING-BOTTOM: 4px; BORDER-LEFT: #cccccc 1px solid; WIDTH: 98%; WORD-BREAK: break-all; PADDING-TOP: 4px; BORDER-BOTTOM: #cccccc 1px solid; BACKGROUND-COLOR: #eeeeee"><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top><SPAN style="COLOR: #0000ff">int</SPAN><SPAN style="COLOR: #000000">&nbsp;f(</SPAN><SPAN style="COLOR: #0000ff">void</SPAN><SPAN style="COLOR: #000000">)<BR><IMG id=Codehighlighter1_12_28_Open_Image onclick="this.style.display='none'; Codehighlighter1_12_28_Open_Text.style.display='none'; Codehighlighter1_12_28_Closed_Image.style.display='inline'; Codehighlighter1_12_28_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockStart.gif" align=top><IMG id=Codehighlighter1_12_28_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_12_28_Closed_Text.style.display='none'; Codehighlighter1_12_28_Open_Image.style.display='inline'; Codehighlighter1_12_28_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedBlock.gif" align=top></SPAN><SPAN id=Codehighlighter1_12_28_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_12_28_Open_Text><SPAN style="COLOR: #000000">{<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">return</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #000000">1</SPAN><SPAN style="COLOR: #000000">;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockEnd.gif" align=top>}</SPAN></SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN></DIV>
<P><BR>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 在加入extern "C"的时候产生的汇编代码是:<BR></P>
<DIV style="BORDER-RIGHT: #cccccc 1px solid; PADDING-RIGHT: 5px; BORDER-TOP: #cccccc 1px solid; PADDING-LEFT: 4px; FONT-SIZE: 13px; PADDING-BOTTOM: 4px; BORDER-LEFT: #cccccc 1px solid; WIDTH: 98%; WORD-BREAK: break-all; PADDING-TOP: 4px; BORDER-BOTTOM: #cccccc 1px solid; BACKGROUND-COLOR: #eeeeee"><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top><SPAN style="COLOR: #000000">&nbsp;&nbsp;&nbsp;&nbsp;.file&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">test.cxx</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;.text<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;.align&nbsp;</SPAN><SPAN style="COLOR: #000000">2</SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>.globl&nbsp;_f<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;.def&nbsp;&nbsp;&nbsp;&nbsp;_f;&nbsp;&nbsp;&nbsp;&nbsp;.scl&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #000000">2</SPAN><SPAN style="COLOR: #000000">;&nbsp;&nbsp;&nbsp;&nbsp;.type&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #000000">32</SPAN><SPAN style="COLOR: #000000">;&nbsp;&nbsp;&nbsp;&nbsp;.endef<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>_f:<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;pushl&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #000000">%</SPAN><SPAN style="COLOR: #000000">ebp<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;movl&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #000000">%</SPAN><SPAN style="COLOR: #000000">esp,&nbsp;</SPAN><SPAN style="COLOR: #000000">%</SPAN><SPAN style="COLOR: #000000">ebp<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;movl&nbsp;&nbsp;&nbsp;&nbsp;$</SPAN><SPAN style="COLOR: #000000">1</SPAN><SPAN style="COLOR: #000000">,&nbsp;</SPAN><SPAN style="COLOR: #000000">%</SPAN><SPAN style="COLOR: #000000">eax<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;popl&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #000000">%</SPAN><SPAN style="COLOR: #000000">ebp<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;ret</SPAN></DIV>
<P><BR>但是不加入了extern "C"之后<BR></P>
<DIV style="BORDER-RIGHT: #cccccc 1px solid; PADDING-RIGHT: 5px; BORDER-TOP: #cccccc 1px solid; PADDING-LEFT: 4px; FONT-SIZE: 13px; PADDING-BOTTOM: 4px; BORDER-LEFT: #cccccc 1px solid; WIDTH: 98%; WORD-BREAK: break-all; PADDING-TOP: 4px; BORDER-BOTTOM: #cccccc 1px solid; BACKGROUND-COLOR: #eeeeee"><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top><SPAN style="COLOR: #000000">&nbsp;.file&nbsp;</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">test.cxx</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>&nbsp;.text<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>&nbsp;.align&nbsp;</SPAN><SPAN style="COLOR: #000000">2</SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>.globl&nbsp;__Z1fv<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>&nbsp;.def&nbsp;__Z1fv;&nbsp;.scl&nbsp;</SPAN><SPAN style="COLOR: #000000">2</SPAN><SPAN style="COLOR: #000000">;&nbsp;.type&nbsp;</SPAN><SPAN style="COLOR: #000000">32</SPAN><SPAN style="COLOR: #000000">;&nbsp;.endef<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>__Z1fv:<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>&nbsp;pushl&nbsp;</SPAN><SPAN style="COLOR: #000000">%</SPAN><SPAN style="COLOR: #000000">ebp<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>&nbsp;movl&nbsp;</SPAN><SPAN style="COLOR: #000000">%</SPAN><SPAN style="COLOR: #000000">esp,&nbsp;</SPAN><SPAN style="COLOR: #000000">%</SPAN><SPAN style="COLOR: #000000">ebp<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>&nbsp;movl&nbsp;$</SPAN><SPAN style="COLOR: #000000">1</SPAN><SPAN style="COLOR: #000000">,&nbsp;</SPAN><SPAN style="COLOR: #000000">%</SPAN><SPAN style="COLOR: #000000">eax<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>&nbsp;popl&nbsp;</SPAN><SPAN style="COLOR: #000000">%</SPAN><SPAN style="COLOR: #000000">ebp<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top>&nbsp;ret</SPAN></DIV>
<P><BR>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 两段汇编代码同样都是使用gcc -S命令产生的,所有的地方都是一样的,<BR>唯独是产生的函数名,一个是_f,一个是__Z1fv.</P>
<P>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; OK,明白了加入与不加入extern "C"之后对函数名称产生的影响,我们继续我们的讨论:为什么需要使用extern "C"呢?<BR>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; C++之父在设计C++之时,考虑到当时已经存在了大量的C代码,为了支持原来的C代码和已经写好C库,需要在C++中尽可能的支持C,而extern "C"就是其中的一个策略.</P>
<P>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 试想这样的情况:一个库文件已经用C写好了而且运行得很良好,这个时候我们需要使用这个库文件,但是我们需要使用C++来写这个新的代码.如果这个代码使用的是C++的方式链接这个C库文件的话,那么就会出现链接错误.我们来看一段代码:首先,我们使用C的处理方式来写一个函数,也就是说假设这个函数当时是用C写成的:</P>
<DIV style="BORDER-RIGHT: #cccccc 1px solid; PADDING-RIGHT: 5px; BORDER-TOP: #cccccc 1px solid; PADDING-LEFT: 4px; FONT-SIZE: 13px; PADDING-BOTTOM: 4px; BORDER-LEFT: #cccccc 1px solid; WIDTH: 98%; WORD-BREAK: break-all; PADDING-TOP: 4px; BORDER-BOTTOM: #cccccc 1px solid; BACKGROUND-COLOR: #eeeeee"><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000">f1.c</SPAN><SPAN style="COLOR: #008000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">extern</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">C</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000"><BR><IMG id=Codehighlighter1_18_46_Open_Image onclick="this.style.display='none'; Codehighlighter1_18_46_Open_Text.style.display='none'; Codehighlighter1_18_46_Closed_Image.style.display='inline'; Codehighlighter1_18_46_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockStart.gif" align=top><IMG id=Codehighlighter1_18_46_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_18_46_Closed_Text.style.display='none'; Codehighlighter1_18_46_Open_Image.style.display='inline'; Codehighlighter1_18_46_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedBlock.gif" align=top></SPAN><SPAN id=Codehighlighter1_18_46_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_18_46_Open_Text><SPAN style="COLOR: #000000">{<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">void</SPAN><SPAN style="COLOR: #000000">&nbsp;f1()<BR><IMG id=Codehighlighter1_30_44_Open_Image onclick="this.style.display='none'; Codehighlighter1_30_44_Open_Text.style.display='none'; Codehighlighter1_30_44_Closed_Image.style.display='inline'; Codehighlighter1_30_44_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedSubBlockStart.gif" align=top><IMG id=Codehighlighter1_30_44_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_30_44_Closed_Text.style.display='none'; Codehighlighter1_30_44_Open_Image.style.display='inline'; Codehighlighter1_30_44_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedSubBlock.gif" align=top></SPAN><SPAN id=Codehighlighter1_30_44_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_30_44_Open_Text><SPAN style="COLOR: #000000">{<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">return</SPAN><SPAN style="COLOR: #000000">;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/ExpandedSubBlockEnd.gif" align=top>}</SPAN></SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockEnd.gif" align=top>}</SPAN></SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN></DIV>
<P>编译命令是:gcc -c f1.c -o f1.o&nbsp;&nbsp; 产生了一个叫f1.o的库文件.<BR>再写一段代码调用这个f1函数:</P>
<DIV style="BORDER-RIGHT: #cccccc 1px solid; PADDING-RIGHT: 5px; BORDER-TOP: #cccccc 1px solid; PADDING-LEFT: 4px; FONT-SIZE: 13px; PADDING-BOTTOM: 4px; BORDER-LEFT: #cccccc 1px solid; WIDTH: 98%; WORD-BREAK: break-all; PADDING-TOP: 4px; BORDER-BOTTOM: #cccccc 1px solid; BACKGROUND-COLOR: #eeeeee"><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000">&nbsp;test.cxx<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000">这个extern表示f1函数在别的地方定义,这样可以通过<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000">编译,但是链接的时候还是需要<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN><SPAN style="COLOR: #008000">//</SPAN><SPAN style="COLOR: #008000">链接上原来的库文件.</SPAN><SPAN style="COLOR: #008000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">extern</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #0000ff">void</SPAN><SPAN style="COLOR: #000000">&nbsp;f1();<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">int</SPAN><SPAN style="COLOR: #000000">&nbsp;main()<BR><IMG id=Codehighlighter1_103_130_Open_Image onclick="this.style.display='none'; Codehighlighter1_103_130_Open_Text.style.display='none'; Codehighlighter1_103_130_Closed_Image.style.display='inline'; Codehighlighter1_103_130_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockStart.gif" align=top><IMG id=Codehighlighter1_103_130_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_103_130_Closed_Text.style.display='none'; Codehighlighter1_103_130_Open_Image.style.display='inline'; Codehighlighter1_103_130_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedBlock.gif" align=top></SPAN><SPAN id=Codehighlighter1_103_130_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_103_130_Open_Text><SPAN style="COLOR: #000000">{<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;f1();<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">return</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #000000">0</SPAN><SPAN style="COLOR: #000000">;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockEnd.gif" align=top>}</SPAN></SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN></DIV>
<P>通过gcc -c&nbsp; test.cxx -o test.o 产生一个叫test.o的文件.<BR>然后,我们使用gcc test.o f1.o来链接两个文件,可是出错了,错误的提示是:<BR>test.o(.text + 0x1f):test.cxx: undefine reference to 'f1()'<BR>也就是说,在编译test.cxx的时候编译器是使用C++的方式来处理f1()函数的,但是实际上链接的库文件却是用C的方式来处理函数的,所以就会出现链接过不去的错误:因为链接器找不到函数.<BR>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;因此,为了在C++代码中调用用C写成的库文件,就需要用extern "C"来告诉编译器:这是一个用C写成的库文件,请用C的方式来链接它们.<BR>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 比如,现在我们有了一个C库文件,它的头文件是f.h,产生的lib文件是f.lib,那么我们如果要在C++中使用这个库文件,我们需要这样写:</P>
<DIV style="BORDER-RIGHT: #cccccc 1px solid; PADDING-RIGHT: 5px; BORDER-TOP: #cccccc 1px solid; PADDING-LEFT: 4px; FONT-SIZE: 13px; PADDING-BOTTOM: 4px; BORDER-LEFT: #cccccc 1px solid; WIDTH: 98%; WORD-BREAK: break-all; PADDING-TOP: 4px; BORDER-BOTTOM: #cccccc 1px solid; BACKGROUND-COLOR: #eeeeee"><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top><SPAN style="COLOR: #0000ff">extern</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">C</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000"><BR><IMG id=Codehighlighter1_11_28_Open_Image onclick="this.style.display='none'; Codehighlighter1_11_28_Open_Text.style.display='none'; Codehighlighter1_11_28_Closed_Image.style.display='inline'; Codehighlighter1_11_28_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockStart.gif" align=top><IMG id=Codehighlighter1_11_28_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_11_28_Closed_Text.style.display='none'; Codehighlighter1_11_28_Open_Image.style.display='inline'; Codehighlighter1_11_28_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedBlock.gif" align=top></SPAN><SPAN id=Codehighlighter1_11_28_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_11_28_Open_Text><SPAN style="COLOR: #000000">{<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>#include&nbsp;</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">f.h</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockEnd.gif" align=top>}</SPAN></SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN></DIV>
<P>回到上面的问题,如果要改正链接错误,我们需要这样子改写test.cxx:<BR></P>
<DIV style="BORDER-RIGHT: #cccccc 1px solid; PADDING-RIGHT: 5px; BORDER-TOP: #cccccc 1px solid; PADDING-LEFT: 4px; FONT-SIZE: 13px; PADDING-BOTTOM: 4px; BORDER-LEFT: #cccccc 1px solid; WIDTH: 98%; WORD-BREAK: break-all; PADDING-TOP: 4px; BORDER-BOTTOM: #cccccc 1px solid; BACKGROUND-COLOR: #eeeeee"><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top><SPAN style="COLOR: #0000ff">extern</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000">C</SPAN><SPAN style="COLOR: #000000">"</SPAN><SPAN style="COLOR: #000000"><BR><IMG id=Codehighlighter1_11_31_Open_Image onclick="this.style.display='none'; Codehighlighter1_11_31_Open_Text.style.display='none'; Codehighlighter1_11_31_Closed_Image.style.display='inline'; Codehighlighter1_11_31_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockStart.gif" align=top><IMG id=Codehighlighter1_11_31_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_11_31_Closed_Text.style.display='none'; Codehighlighter1_11_31_Open_Image.style.display='inline'; Codehighlighter1_11_31_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedBlock.gif" align=top></SPAN><SPAN id=Codehighlighter1_11_31_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_11_31_Open_Text><SPAN style="COLOR: #000000">{<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">extern</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #0000ff">void</SPAN><SPAN style="COLOR: #000000">&nbsp;f1();<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockEnd.gif" align=top>}</SPAN></SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN><SPAN style="COLOR: #0000ff">int</SPAN><SPAN style="COLOR: #000000">&nbsp;main()<BR><IMG id=Codehighlighter1_45_72_Open_Image onclick="this.style.display='none'; Codehighlighter1_45_72_Open_Text.style.display='none'; Codehighlighter1_45_72_Closed_Image.style.display='inline'; Codehighlighter1_45_72_Closed_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockStart.gif" align=top><IMG id=Codehighlighter1_45_72_Closed_Image style="DISPLAY: none" onclick="this.style.display='none'; Codehighlighter1_45_72_Closed_Text.style.display='none'; Codehighlighter1_45_72_Open_Image.style.display='inline'; Codehighlighter1_45_72_Open_Text.style.display='inline';" src="http://www.cppblog.com/images/OutliningIndicators/ContractedBlock.gif" align=top></SPAN><SPAN id=Codehighlighter1_45_72_Closed_Text style="BORDER-RIGHT: #808080 1px solid; BORDER-TOP: #808080 1px solid; DISPLAY: none; BORDER-LEFT: #808080 1px solid; BORDER-BOTTOM: #808080 1px solid; BACKGROUND-COLOR: #ffffff"><IMG src="http://www.cppblog.com/images/dot.gif"></SPAN><SPAN id=Codehighlighter1_45_72_Open_Text><SPAN style="COLOR: #000000">{<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;f1();<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/InBlock.gif" align=top>&nbsp;&nbsp;&nbsp;&nbsp;</SPAN><SPAN style="COLOR: #0000ff">return</SPAN><SPAN style="COLOR: #000000">&nbsp;</SPAN><SPAN style="COLOR: #000000">0</SPAN><SPAN style="COLOR: #000000">;<BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/ExpandedBlockEnd.gif" align=top>}</SPAN></SPAN><SPAN style="COLOR: #000000"><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top><BR><IMG src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align=top></SPAN></DIV>
<P>重新编译并且链接就可以过去了.</P>
<P>总结:C和C++对函数的处理方式是不同的.extern "C"是使C++能够调用C写作的库文件的一个手段,如果要对编译器提示使用C的方式来处理函数的话,那么就要使用extern "C"来说明.</P>
<P>&nbsp;</P>
<P>&nbsp;</P>
<P>&nbsp;</P><img src ="http://www.cppblog.com/converse/aggbug/2733.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/converse/" target="_blank">创</a> 2006-01-14 23:52 <a href="http://www.cppblog.com/converse/archive/2006/01/14/2733.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item></channel></rss>