类的三要素:封装、继承、多态
概述
![](https://i-blog.csdnimg.cn/blog_migrate/dcedd1948269e8c871724bc092c524b1.png)
举例:
![](https://i-blog.csdnimg.cn/blog_migrate/b20ce53277b02b1d147789f27df5dcda.png)
![](https://i-blog.csdnimg.cn/blog_migrate/8738bd90269eea35614aad7e96337332.png)
验证环境中的案例1
![](https://i-blog.csdnimg.cn/blog_migrate/bb3890f4017ec7665a86a92579900e0a.png)
![](https://i-blog.csdnimg.cn/blog_migrate/659b0237c4bbdec9b28db738615c9200.png)
![](https://i-blog.csdnimg.cn/blog_migrate/f53d7f247c70cd2ce015df23b67f920a.png)
![](https://i-blog.csdnimg.cn/blog_migrate/f72b1291b567c8a07d3b71560489c6fd.png)
-
BadTr继承了父类的成员变量,又新定义了成员变量和方法。默认二者的方法没有关系,但是通过了super来继承了父类的calc_crc()和display(),两个方法。
-
不使用super.calc_crc()的话,使用this.calc_crc()在当前子类找calc.crc(),找不到就自动到父类中寻找calc.crc(),结果是找到了。说明this和super有区别也有联系。
验证环境中的案例2
![](https://i-blog.csdnimg.cn/blog_migrate/59f1fa551fda176356ffa8b82cbb8a1d.png)
![](https://i-blog.csdnimg.cn/blog_migrate/2f3b8731226e1139df9187dd165f9f41.png)
![](https://i-blog.csdnimg.cn/blog_migrate/6c637b1d2883e76aa82224415f165ac0.png)
![](https://i-blog.csdnimg.cn/blog_migrate/c7cd20cc352707e55bfc86faa546a33c.png)
-
默认情况下,子类继承语句之后,新定义了一个与父类的方法,通常喜欢把父类的方法写在前面,开辟空间。
-
成员变量默认值赋予之后,才会进入new函数中执行剩下的初始化代码。如下图所示,先赋初值,再执行new函数的代码,进行初始化。
![](https://i-blog.csdnimg.cn/blog_migrate/13b84aa10c5fc9c97f4a78eb3a00cc87.png)
成员的覆盖
![](https://i-blog.csdnimg.cn/blog_migrate/2ef5fbeed3516894a34cf79cc76d44e6.png)
![](https://i-blog.csdnimg.cn/blog_migrate/f0081d5a82a2dd7b004ee2642d544196.png)
如图所示,子类中定义了def = 200,父类中也有def = 100。
![](https://i-blog.csdnimg.cn/blog_migrate/b593443bf7ebbc7b7046095accf354c3.png)
![](https://i-blog.csdnimg.cn/blog_migrate/1c6493df69750c1a61793cd3c550d4fc.png)
-
子类继承父类后,可以指向父类中public的全部成员变量和方法,因此子类可以指向父类的def和自身子类的def,但是使用wr.def,那么优先指向子类中的def,为200。
-
而t = wr之后,虽然说把wr全部给了t,此时wr和t都指向同一个对象(该对象继承了父类的成员变量def)但是t作为父类,依旧只能指向从wr那赋值而来的两个def中父类的def,因此def=100。
-
wr = t;这样的赋值会报错,因为父类句柄的空间更小,而子类句柄的空间更大 。t父类小三角没办法扩大成一个大三角。wr = t之后使用wr.def这句话是没办法实现的,会报错,因为此时wr指向t的内存空间是小三角形,而原本的子类的def在扩展的小三角形之外的空间内,因此没办法取到,不能扩大为一个大三角形。
-
即,父类句柄不能直接赋值给子类句柄(用“=”是错误的),而是要使用$cast()语句,把父类句柄转化为子类句柄。
-
$cast(wr,t);即把父类句柄转化为子类句柄。如果t指向了大三角形则返回1,反之则为0;
![](https://i-blog.csdnimg.cn/blog_migrate/3ec654c113c2aaa685707d252f112e11.png)
![](https://i-blog.csdnimg.cn/blog_migrate/93dc702223b3050332711454412f4711.png)
句柄的使用
![](https://i-blog.csdnimg.cn/blog_migrate/7c4d87604bd64a3be778c2e9e9f74670.png)
![](https://i-blog.csdnimg.cn/blog_migrate/83c3e5ff5bd9d8a96696a7fba91cbb1c.png)
![](https://i-blog.csdnimg.cn/blog_migrate/df5336057bff2002e6bcc6cd21c98f4b.png)
答案:C;会报错,因为Transaction tr默认tr方向为input,只是把null通过create传递给了tr,但是tr为input并不会输出,因此得不到t.addr的值。
因此修改如下:修改参数列表ref Transaction tr或者inout Transaction tr。
句柄的动态修改
![](https://i-blog.csdnimg.cn/blog_migrate/ddff10c37c016c4f2bd618c6f8a701c2.png)
![](https://i-blog.csdnimg.cn/blog_migrate/51925534299baa03e489317267c6ac0f.png)
0 << 2 = 0、1 << 2 = 4、2 << 2 = 8;