java向上转型文档格式.docx
- 文档编号:3312871
- 上传时间:2023-05-01
- 格式:DOCX
- 页数:8
- 大小:16.07KB
java向上转型文档格式.docx
《java向上转型文档格式.docx》由会员分享,可在线阅读,更多相关《java向上转型文档格式.docx(8页珍藏版)》请在冰点文库上搜索。
publicvoida1(){
System.out.println("
Superclass"
);
}
A的子类B:
publicclassBextendsA{
Childrenclass"
//覆盖父类方法
publicvoidb1(){}//B类定义了自己的新方法
C类:
publicclassC{
publicstaticvoidmain(String[]args){
Aa=newB();
//向上转型
a.a1();
如果运行C,输出的是Superclass还是Childrenclass?
不是你原来预期的Superclass,而是Childrenclass。
这是因为a实际上指向的是一个子类对象。
当然,你不用担心,Java虚拟机会自动准确地识别出究竟该调用哪个具体的方法。
不过,由于向上转型,a对象会遗失和父类不同的方法,例如b1()。
有人可能会提出疑问:
这不是多此一举吗?
我们完全可以这样写:
Ba=newB();
a.a1();
确实如此!
但这样就丧失了面向抽象的编程特色,降低了可扩展性。
其实,不仅仅如此,向上转型还可以减轻编程工作量。
来看下面的显示器类Monitor:
publicclassMonitor{
publicvoiddisplayText(){}
publicvoiddisplayGraphics(){}
液晶显示器类LCDMonitor是Monitor的子类:
publicclassLCDMonitorextendsMonitor{
publicvoiddisplayText(){
LCDdisplaytext"
publicvoiddisplayGraphics(){
LCDdisplaygraphics"
阴极射线管显示器类CRTMonitor自然也是Monitor的子类:
publicclassCRTMonitorextendsMonitor{
CRTdisplaytext"
CRTdisplaygraphics"
等离子显示器PlasmaMonitor也是Monitor的子类:
publicclassPlasmaMonitorextendsMonitor{
Plasmadisplaytext"
Plasmadisplaygraphics"
现在有一个MyMonitor类。
假设没有向上转型,MyMonitor类代码如下:
publicclassMyMonitor{
run(newLCDMonitor());
run(newCRTMonitor());
run(newPlasmaMonitor());
publicstaticvoidrun(LCDMonitormonitor){
monitor.displayText();
monitor.displayGraphics();
publicstaticvoidrun(CRTMonitormonitor){
publicstaticvoidrun(PlasmaMonitormonitor){
可能你已经意识到上述代码有很多重复代码,而且也不易维护。
有了向上转型,代码可以更为简洁:
publicstaticvoidrun(Monitormonitor){//父类实例作为参数
我们也可以采用接口的方式,例如:
publicinterfaceMonitor{
abstractvoiddisplayText();
abstractvoiddisplayGraphics();
将液晶显示器类LCDMonitor稍作修改:
publicclassLCDMonitorimplementsMonitor{
CRTMonitor、PlasmaMonitor类的修改方法与LCDMonitor类似,而MyMonitor可以不不作任何修改。
可以看出,向上转型体现了类的多态性,增强了程序的简洁性。
5.13.2向下转型
子类转型成父类是向上转型,反过来说,父类转型成子类就是向下转型。
但是,向下转型可能会带来一些问题:
我们可以说麻雀是鸟,但不能说鸟就是麻雀。
来看下面的例子:
A类:
voidaMthod(){
Amethod"
voidbMethod1(){
Bmethod1"
voidbMethod2(){
Bmethod2"
publicstaticvoidmain(String[]args){
Aa1=newB();
//向上转型
a1.aMthod();
//调用父类aMthod(),a1遗失B类方法bMethod1()、bMethod2()
Bb1=(B)a1;
//向下转型,编译无错误,运行时无错误
b1.aMthod();
//调用父类A方法
b1.bMethod1();
//调用B类方法
b1.bMethod2();
Aa2=newA();
Bb2=(B)a2;
//向下转型,编译无错误,运行时将出错
b2.aMthod();
b2.bMethod1();
b2.bMethod2();
}
从上面的代码我们可以得出这样一个结论:
向下转型需要使用强制转换。
运行C程序,控制台将输出:
Exceptioninthread"
main"
java.lang.ClassCastException:
a.b.Acannotbecasttoa.b.Bat
a.b.C.main(C.java:
14)
Amethod
Bmethod1
Bmethod2
其实黑体部分的向下转型代码后的注释已经提示你将发生运行时错误。
为什么前一句向下转型代码可以,而后一句代码却出错?
这是因为a1指向一个子类B的对象,所以子类B的实例对象b1当然也可以指向a1。
而a2是一个父类对象,子类对象b2不能指向父类对象a2。
那么如何避免在执行向下转型时发生运行时ClassCastException异常?
使用5.7.7节学过的instanceof就可以了。
我们修改一下C类的代码:
Aa2=newA();
if(a2instanceofB){
Bb2=(B)a2;
b2.aMthod();
b2.bMethod1();
b2.bMethod2();
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- java 向上 转型