C++编程开发教程从零开始

  次阅读 作者:智能小宝 来源:互联网 2016-01-26 10:33 我要评论(0)

本文的中篇已经介绍了虚的意思,就是要间接获得,并且举例说明电视机的频道就是让人间接获得电视台频率的,因此其从这个意义上说是虚的,因为它可能操作失败--某个频道还未调好而导致一片雪花。并且说明了间接的好处,就是只用编好一段代码(按5频

道),则每次执行它时可能有不同结果(今天5频道被设置成中央5台,明天可以被定成中央2台),进而使得前面编的程序(按5频道)显得很灵活。注意虚之所以能够很灵活是因为它一定通过 一种手段 来间接达到目的,如每个频道记录着一个频率。但这是不够的,一定还有 另一段代码 能改变那种手段的结果(频道记录的频率),如调台。

先看虚继承。它间接从子类的实例中获得父类实例的所在位置,通过虚类表实现(这是 一种手段 ),接着就必须能够有 另一段代码 来改变虚类表的值以表现其灵活性。首先可以自己来编写这段代码,但就要求清楚编译器将虚类表放在什么地方,而不同的编译器有不同的实现方法,则这样编写的代码兼容性很差。C++当然给出了 另一段代码 ,就是当某个类在同一个类继承体系中被多次虚继承时,就改变虚类表的值以使各子类间接获得的父类实例是同一个。此操作的功能很差,仅仅只是节约内存而已。

如:

struct A { long a; };

struct B : virtual public A { long b; }; struct C : virtual public A { long c; };

struct D : public B, public C { long d; };

这里的D中有两个虚类表,分别从B和C继承而来,在D的构造函数中,编译器会编写必要的代码以正确初始化D的两个虚类表以使得通过B继承的虚类表和通过C继承的虚类表而获得的A的实例是同一个。

再看虚函数。它的地址被间接获得,通过虚函数表实现(这是 一种手段 ),接着就必须还能改变虚函数表的内容。同上,如果自己改写,代码的兼容性很差,而C++也给出了 另一段代码 ,和上面一样,通过在派生类的构造函数中填写虚函数表,根据当前派生类的情况来书写虚函数表。它一定将某虚函数表填充为当前派生类下,类型、名字和原来被定义为虚函数的那个函数尽量匹配的函数的地址。

如:

struct A { virtual void ABC(), BCD( float ), ABC( float ); };

struct B : public A { virtual void ABC(); };

struct C : public B { void ABC( float ), BCD( float ); virtual float CCC( double ); };

struct D : public C { void ABC(), ABC( float ), BCD( float ); };

在A::A中,将两个A::ABC和一个A::BCD的地址填写到A的虚函数表中。

在B::B中,将B::ABC和继承来的B::BCD和B::ABC填充到B的虚函数表中。

在C::C中,将C::ABC、C::BCD和继承来的C::ABC填充到C的虚函数表中,并添加一个元素:C::CCC。

在D::D中,将两个D::ABC和一个D::BCD以及继承来的D::CCC填充到D的虚函数表中。

这里的D是依次继承自A、B、C,并没有因为多重继承而产生两个虚函数表,其只有一个虚函数表。虽然D中的成员函数没有用virtual修饰,但它们的地址依旧被填到D的虚函数表中,因为virtual只是表示使用那个成员函数时需要间接获得其地址,与是否填写到虚函数表中没有关系。

电视机为什么要用频道来间接获得电视台的频率?因为电视台的频率人不容易记,并且如果知道一个频率,慢慢地调整共谐电容的电容值以使电路达到那个频率效率很低下。而做10组共谐电路,每组电路的电容值调好后就不再动,通过切换不同的共谐电路来实现快速转换频率。因此间接还可以提高效率。还有,5 频道本来是中央5台,后来看腻了把它换成中央2台,则同样的动作(按5频道)将产生不同的结果, 按5频道 这个程序编得很灵活。

由上面,至少可以知道:间接用于简化操作、提高效率和增加灵活性。这里提到的间接的三个用处都基于这么一个想法--用 一种手段 来达到目的,用 另一段代码 来实现上面提的用处。而C++提供的虚继承和虚函数,只要使用虚继承来的成员或虚函数就完成了 一种手段 。而要实现 另一段代码 ,从上面的说明中可以看出,需要通过派生的手段来达到。在派生类中定义和父类中声明的虚函数原型相同的函数就可以改变虚函数表,而派生类的继承体系中只有重复出现了被虚继承的类才能改变虚类表,而且也只是都指向同一个被虚继承的类的实例,远没有虚函数表的修改方便和灵活,因此虚继承并不常用,而虚函数则被经常的使用。

虚的使用

由于C++中实现 虚 的方式需要借助派生的手段,而派生是生成类型,因此 虚 一般映射为类型上的间接,而不是上面频道那种通过实例(一组共谐电路)来实现的间接。注意 简化操作 实际就是指用函数映射复杂的操作进而简化代码的编写,利用函数名映射的地址来间接执行相应的代码,对于虚函数就是一种调用形式表现多种执行结果。而 提高效率 是一种算法上的改进,即频道是通过重复十组共谐电路来实现的,正宗的空间换时间,不是类型上的间接可以实现的。因此C++中的 虚 就只能增加代码的灵活性和简化操作(对于上面提出的三个间接的好处)。

C++

本站文章信息来源于网络以及网友投稿,本站只负责对文章进行整理、排版、编辑,是出于传递更多信息之目的,并不意味着赞同其观点或证实其内容的真实性。如果您有什么意见或建议,请联系QQ28-1688-302!

人工智能实验室
相关文章相关文章
  • 未来两年人工智能要怎么走?看这篇就够了

    未来两年人工智能要怎么走?看这篇就够了

  • 无人驾驶汽车如何改变城市生活?听听他们怎么说

    无人驾驶汽车如何改变城市生活?听听他们怎么说

  • 英国研发“杀生”机器人 通过生命体获取能量

    英国研发“杀生”机器人 通过生命体获取能量

  • 韩春雨称已能重复实验结果 近期将有消息公布

    韩春雨称已能重复实验结果 近期将有消息公布

网友点评网友点评
阅读推荐阅读推荐

据国外媒体报道,在过去两年内,聊天机器人(chatbot)、人工智能以及机器学习的研发和采用取得了巨大进展。许多初创公司正利用人工智能和...

霍金 视觉中国 图 英国著名物理学家霍金(Stephen Hawking)再次就人工智能(AI)发声,他认为:对于人类来说,强大AI的出现可能是最美妙的...

文|郑娟娟 今年,人工智能(AI) 60岁了。在AI60岁的时候,笔者想要介绍一下AI100,一个刚刚2岁的研究项目,但它的预设寿命是100年,甚至更长...

AlphaGo与李世石的人机大战,为大众迅速普及了人工智能的概念。 但对谷歌而言,除了下围棋,现在的人工智能进展到哪一步了?未来,人工智能...