当前位置:C++技术网 > 精选软件 > 关于父子对象相互赋值以及多态特性的分析:2 父类对象赋值给子类对象的理解

关于父子对象相互赋值以及多态特性的分析:2 父类对象赋值给子类对象的理解

更新时间:2017-08-20 09:07:28浏览次数:1+次

       接上一篇。。。

    2.父类对象赋值给子类对象的理解

    我们再来看一段代码:
A a;
AA aa2 = a;
aa2.show();
aa2.say();

    我们这里定义一个对象aa2,然后来尝试用父类对象赋值给子类对象。结果会报错,错误提示为:error : conversion from 'A' to non-scalar type 'AA' requested,意思就是,需要的类型是AA,赋值的确实A,而AA是从A继承而来,所以是non-scalar(非同级)的类型。为什么是non-scalar而不是不兼容或者不同类型的呢?A和AA两种类型,不能说是不兼容的,而是要看如何兼容。所以说不兼容类型是不妥的,否则子类对象赋值给父类对象怎么说的过去呢!那说类型不同,更是错误。而non-scalar非同级类型也就表示的有继承的类型关系,只是使用的不妥,造成了转换类型会有问题。
    我们来看看为什么会不妥,这也就是报错的原因。
    A类和AA或BB的内存空间结构是不一样的。AA或BB的内存结构是涵盖了A的,AA或BB的内存结构是包含了A的。当我们用子类对象如aa赋值给父类对象a的时候,我们是将aa整个大内存盖到a这个小内存去。a是需求方,只需要含show函数的那一块内存的数据就可以了。而aa或bb都不止满足了a的需求,还有更多的数据可以提供。而对于a来说,信息有多余的,需要的信息都是完整的。在我们的意识里,刚好满足是最完美的,但是如果比刚好需要的还要多,自然也是不错的。我们只要丢掉多余的信息即可。那么这个赋值动作没有任何问题。
    但是如果将父类对象a赋值给子类对象aa或bb时,aa或bb期望的不仅是包含show的内存的数据,还期望了包含say函数的内存的数据。而父类对象a并不能满足这个需求,只能提供包含show函数的内存的数据。这样一来,aa或bb就吃不饱了。吃不饱就有很大问题了。前面说的是信息有多,那叫做吃饱了还可以吃点饭后甜点,想吃就吃不吃也可以。但是此时的情况就是,压根就吃不饱。吃不饱就有民怨了。所以吃不饱的机制就有问题。
    那是不是吃不饱就一定不行呢?不一定。看设计者如何去实现。如果他设计的是吃不饱就不合理,那么这就会有语法错误。如果设计的是吃不饱也可以凑合,那么得到的部分就赋值,得不到的部分就不管它。然而不管的这部分,就是未初始化的。未初始化的数据如果拿去使用,必然会出现问题的。而我们通常赋值的习惯都是全部能够赋值或者初始化的,所以这样存在未初始化的设计,就有点不妥,就有安全隐患了。所以为了规避这样的设计缺陷,就必须要保证可以多吃,但不能少吃。
    这也就是为什么父类对象不能赋值给子类对象的原因。