⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 [23] inheritance what your mother never told you, c++ faq lite.htm

📁 c++faq。里面有很多关于c++的问题的解答。
💻 HTM
📖 第 1 页 / 共 2 页
字号:
<HR>

<P><A name=[23.3]></A>
<DIV class=FaqTitle>
<H3>[23.3] 当基类构造函数调用虚函数时,为什么不调用派生类重写的该虚函数?</H3></DIV>
<P>当基类被构造时,对象还不是一个派生类的对象,所以如果&nbsp;<TT>Base::Base()</TT>调用了<A 
href="http://www.sunistudio.com/cppfaq/virtual-functions.html">虚函数</A> 
<TT>virt()</TT>,则&nbsp;<TT>Base::virt()</TT>&nbsp;将被调用,即使&nbsp;<TT>Derived::virt()</TT>(译注:即派生类重写的虚函数)存在。<BR><BR>同样,当基类被析构时,对象已经不再是一个派生类对象了,所以如果&nbsp;<TT>Base::~Base()</TT>调用了<TT>virt()</TT>,则&nbsp;<TT>Base::virt()</TT>得到控制权,而不是重写的&nbsp;<TT>Derived::virt()</TT> 
。<BR><BR>当你可以想象到如果&nbsp;<TT>Derived::virt()</TT>&nbsp;涉及到派生类的某个成员对象将造成的灾难的时候,你很快就能看到这种方法的明智。详细来说,如果&nbsp;<TT>Base::Base()</TT>调用了虚函数&nbsp;<TT>virt()</TT>,这个规则使得&nbsp;<TT>Base::virt()</TT>被调用。如果不按照这个规则,<TT>Derived::virt()</TT>将在派生对象的派生部分被构造之前被调用,此时属于派生对象的派生部分的某个成员对象还没有被构造,而&nbsp;<TT>Derived::virt()</TT>却能够访问它。这将是灾难。
<P><SMALL>[&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/strange-inheritance.html#top">Top</A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/strange-inheritance.html#bottom">Bottom</A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/abcs.html">Previous&nbsp;section</A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/private-inheritance.html">Next&nbsp;section</A> 
]</SMALL> 
<HR>

<P><A name=[23.4]></A>
<DIV class=FaqTitle>
<H3>[23.4] 派生类可以重置(“覆盖”)基类的非虚函数吗?</H3></DIV>
<P>合法但不合理。 
<P>有经验的&nbsp;C++&nbsp;程序员有时会重新定义非虚函数(例如,派生类的实现可能可以更有效地利用派生类的资源),或者为了回避<A 
href="http://www.sunistudio.com/cppfaq/strange-inheritance.html#[23.5]">隐藏规则</A>。即使非虚函数的指派基于指针/引用的静态类型而不是指针/引用所指对象的动态类型,但其客户可见性必须是一致的。 

<P><SMALL>[&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/strange-inheritance.html#top">Top</A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/strange-inheritance.html#bottom">Bottom</A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/abcs.html">Previous&nbsp;section</A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/private-inheritance.html">Next&nbsp;section</A> 
]</SMALL> 
<HR>

<P><A name=[23.5]></A>
<DIV class=FaqTitle>
<H3>[23.5] 
“<TT>Warning:&nbsp;Derived::f(float)&nbsp;hides&nbsp;Base::f(int)</TT>”&nbsp;是什么意思?</H3></DIV>
<P>意思是:你要完蛋了。
<P>你所处的困境是:如果基类声明了一个成员函数<TT>f(int)</TT>,并且派生类声明了一个成员函数&nbsp;<TT>f(float)</TT>(名称相同,但参数类型和/或数量不同),那么&nbsp;<TT>Base</TT>&nbsp;的&nbsp;<TT>f(int)</TT>被隐藏(hidden)而不是被重载(overloaded)或被重写(overridden)(即使&nbsp;基类的<TT>f(int)</TT>是<A 
href="http://www.sunistudio.com/cppfaq/virtual-functions.html">虚拟</A>的)
<P>以下是你如何摆脱困境:派生类必须有一个被隐藏成员函数的<TT>using</TT>&nbsp;声明,例如: 
<P>
<DIV 
class=CodeBlock><TT>&nbsp;class&nbsp;Base&nbsp;{<BR>&nbsp;public:<BR>&nbsp;&nbsp;&nbsp;void&nbsp;f(int);<BR>&nbsp;};<BR>&nbsp;<BR>&nbsp;class&nbsp;Derived&nbsp;:&nbsp;public&nbsp;Base&nbsp;{<BR>&nbsp;public:<BR>&nbsp;&nbsp;&nbsp;using&nbsp;Base::f;&nbsp;&nbsp;&nbsp;&nbsp;</TT><EM>//&nbsp;This&nbsp;un-hides&nbsp;<TT>Base::f(int)</TT></EM><TT><BR>&nbsp;&nbsp;&nbsp;void&nbsp;f(double);<BR>&nbsp;}; 
</TT></DIV>
<P>如果你的编译器不支持<TT>using</TT>语法,那么就重新定义基类的被隐藏的成员函数,<A 
href="http://www.sunistudio.com/cppfaq/strange-inheritance.html#[23.4]">即使它们是非虚的</A>。一般来说这种重定义只不过使用<TT>::</TT>语法调用了基类被隐藏的成员函数,如, 

<P>
<DIV 
class=CodeBlock><TT>&nbsp;class&nbsp;Derived&nbsp;:&nbsp;public&nbsp;Base&nbsp;{<BR>&nbsp;public:<BR>&nbsp;&nbsp;&nbsp;void&nbsp;f(double);<BR>&nbsp;&nbsp;&nbsp;void&nbsp;f(int&nbsp;i)&nbsp;{&nbsp;Base::f(i);&nbsp;}&nbsp;&nbsp;</TT><EM>//&nbsp;The&nbsp;redefinition&nbsp;merely&nbsp;calls&nbsp;<TT>Base::f(int)</TT></EM><TT><BR>&nbsp;}; 
</TT></DIV>
<P><SMALL>[&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/strange-inheritance.html#top">Top</A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/strange-inheritance.html#bottom">Bottom</A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/abcs.html">Previous&nbsp;section</A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/private-inheritance.html">Next&nbsp;section</A> 
]</SMALL> 
<HR>

<P><A name=[23.6]></A>
<DIV class=FaqTitle>
<H3>[23.6]&nbsp; "virtual table" is an unresolved external 是什么意思?</H3></DIV>
<P>如果你得到一个连接错误"<TT>Error:&nbsp;Unresolved&nbsp;or&nbsp;undefined&nbsp;symbols&nbsp;detected:&nbsp;virtual&nbsp;table&nbsp;for&nbsp;class&nbsp;Fred</TT>",那么可能是你在&nbsp;<TT>Fred</TT>&nbsp;类中有一个未定义的<A 
href="http://www.sunistudio.com/cppfaq/virtual-functions.html">虚</A>成员函数。<BR><BR>编译器通常会为含有虚函数的类创建一个称为“虚函数表”的不可思议的数据结构(这就是它如何处理<A 
href="http://www.sunistudio.com/cppfaq/virtual-functions.html#[20.2]">动态绑定</A>的)。通常你根本不必知道它。但如果你忘了为<TT>Fred</TT>&nbsp;类定义一个虚函数,则有时会得到这个连接错误。<BR><BR>许多编译器将这个不可思议的“虚函数表”放进定义类的第一个非内联虚函数的编辑单元中。因此如果&nbsp;<TT>Fred</TT>&nbsp;类的第一个非内联虚函数是&nbsp;<TT>wilma()</TT>,那么编译器会将&nbsp;<TT>Fred</TT>&nbsp;的虚函数表放在&nbsp;<TT>Fred::wilma()</TT>&nbsp;所在的编辑单元里。不幸的是如果你意外的忘了定义&nbsp;<TT>Fred::wilma()</TT>,那么你会得到一个"<TT>Fred</TT>'s 
virtual table is undefined"(<TT>Fred</TT>的虚函数表未定义)的错误而不是“<TT>Fred::wilma()</TT> 
is undefined”(<TT>Fred::wilma()</TT>未定义)。
<P><SMALL>[&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/strange-inheritance.html#top">Top</A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/strange-inheritance.html#bottom">Bottom</A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/abcs.html">Previous&nbsp;section</A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/private-inheritance.html">Next&nbsp;section</A> 
]</SMALL> 
<HR>

<P><A name=bottom></A><A href="mailto:cline@parashift.com"><IMG height=26 
alt=E-Mail 
src="[23] Inheritance what your mother never told you, C++ FAQ Lite.files/mbox.gif" 
width=89>&nbsp;E-mail the author</A><BR>[&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/index.html"><EM>C++ FAQ Lite</EM></A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/index.html#table-of-contents">Table&nbsp;of&nbsp;contents</A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/subject-index.html">Subject&nbsp;index</A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/copy-permissions.html#[1.1]">About&nbsp;the&nbsp;author</A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/copy-permissions.html#[1.2]">&copy;</A> 
|&nbsp;<A 
href="http://www.sunistudio.com/cppfaq/on-line-availability.html#[2.2]">Download&nbsp;your&nbsp;own&nbsp;copy</A>&nbsp;]<BR><SMALL>Revised 
Apr 8, 2001</SMALL> </P></BODY></HTML>

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -