向上转型 向下转型

如父类Animal,子类Cat,Dog。其中Animal可以是类也可以是接口,Cat和Dog是继承或实现Animal的子类。
Animal animal = new Cat();
声明的是父类,实际指向的是子类的一个对象。
理解多态,首先要知道“向上转型”。
我定义了一个子类Cat,它继承了Animal类,那么后者就是前者是父类。我可以通过
Cat c = new Cat();
实例化一个Cat的对象,这个不难理解。但当我这样定义时:
Animal a = new Cat();
这代表什么意思呢? 很简单,它表示我定义了一个Animal类型的引用,指向新建的Cat类型的对象。 由于Cat是继承自它的父类Animal,所以Animal类型的引用是可以指向Cat类型的对象的。这就是“向上转型”。

那么这样做有什么意义呢?因为子类是对父类的一个改进和扩充,所以一般子类在功能上较父类更强大,属性较父类更独特, 定义一个父类类型的引用指向一个子类的对象既可以使用子类强大的功能,又可以抽取父类的共性。 所以,父类类型的引用可以调用父类中定义的所有属性和方法,而对于子类中定义而父类中没有的方法, 父类引用是无法调用的

【具体的意思就是:现在Cat继承自Animal,Cat里面对于父类的方法进行了扩充和更强大的定义,通过向上转型调用这些强大的方法,但是对于子类定义父类没有的方法,向上转型不能使用】

那什么是动态链接呢?当父类中的一个方法只有在父类中定义而在子类中没有重写的情况下,才可以被父类类型的引用调用; 对于父类中定义的方法,如果子类中重写了该方法,那么父类类型的引用将会调用子类中的这个方法,这就是动态连接。
下面看一个例子:
class Parent1 { int i = 20; int j = 30; void f() { System.out.print("" + i); } } public class Child extends Parent1 { int i = 30; int k = 40; void f() { System.out.print(" " + i); } void g() { System.out.print("" + k); } public static void main(String args[]) { Parent1 x = new Child(); System.out.print(x.i); x.f(); Child x1 = (Child) x; System.out.print("" + x1.i); x1.f(); } }
上面的程序是个很典型的多态的例子。子类Child继承了父类Parent1,并重写了父类的void f()方法,那么父类类型的引用child在调用该方法时将会调用子类中重写的void f()
程序流程如下:
//创建一个父类的引用指向子类,称之为向下转型,x.i调用的是父类的属性 //而下面的x.f()因为子类重写了f方法所以除数的是子类的30 //如果没有重写僵尸调用父类的20 Parent1 x = new Child(); System.out.print(x.i); x.f();

/创建一个子类对象指向子类本身,就是调用自己的属性和方法 //所以输出的是自己的30,30 Child x1 = (Child) x; System.out.print("" + x1.i); x1.f();
对于多态,可以总结以下几点:
一、使用父类类型的引用指向子类的对象;
二、该引用只能调用父类中定义的方法和变量;
三、如果子类中重写了父类中的一个方法,那么在调用这个方法的时候,将会调用子类中的这个方法;(动态连接、动态调用)
四、变量不能被重写(覆盖),”重写“的概念只针对方法,如果在子类中”重写“了父类中的变量,那么在编译时会报错。
另转载:
多态是通过:
1 接口 和 实现接口并覆盖接口中同一方法的几不同的类体现的
2 父类 和 继承父类并覆盖父类中同一方法的几个不同子类实现的.
向下转型:[调用子类特有的属性/方法]
情况一:
如果父类引用的对象是指向子类的对象,那么在向下转型的过程中是安全的。也就是编译是不会出错误的。
情况二:
如果父类引用的对象是父类本身对象,那么在向下转型的过程中是不安全的,编译不会出错,但是运行时会出现java.lang.ClassCastException错误
【即无论向上还是向下转型,首先father f = new son() 这句话都是前提
而对于向下转型,在这句话的基础上进行Son s = (Son) s是安全的
但是如果是father f = new father();Son s = (Son) f 则会出现编译时没问题,运行时报错】
class Base { } class Sub extends Base { } class Sub2 extends Base { } public class Cex { public static void main(String argv[]) { Base b = new Base(); Sub s = (Sub) b; } }
程序出现问题如下,在创建了一个父类引用指向父类的时候,在向下转型的时候就是不安全的,爆出java.lang.ClassCastException错误。

猜你喜欢

转载自blog.csdn.net/weixin_38964895/article/details/81019607