如果大家明白了的话,我们就可以从上述公式推导出结论,所有的子类都可以作为父类的类型(同一种类型)来对待。像刚才那个动物有很多子类啊,可以有很多对象。动物 a=new 猫();动物 b=new 狗(); 动物 c=new 猪();。这样的将子类型的对象引用转换成父类型的对象引用,叫做上溯造型(upcasting)。
我们再来引伸一下,我们在数组那节课里讲了,数组存放的元素是相同类型的数据,但是上溯造型使得java允许创建不同类型对象的数组。例如:
Employee[] staff = new
Employee[3];
staff[0] = new
Manager();
staff[1] = new
Secretary();
staff[2] = new Employee();
夷?这是怎么回事啊,数组里面不是相同类型吗?对啊,因为Sectetary和Manager是Employee的子类,所以也可以通过上溯造型变成Employee啊。以前我们还学到了所有对象都是从java.lang.Object 继承下来的。如果数组要是 Object型的话 Object[] obj=new
Object[];那就是里面放什么对象都行了。因为什么对象都可以是Object型的。
实践:
//
java中的多态
class Shape {
void draw()
{}
void erase() {}
}
//圆形
class Circle extends Shape {
void draw() {
System.out.println("Circle.draw()");
}
void erase() {
System.out.println("Circle.erase()");
}
}
//正方形
class Square extends Shape
{
void draw() {
System.out.println("Square.draw()");
}
void erase() {
System.out.println("Square.erase()");
}
}
//三角形
class Triangle extends Shape {
void draw() {
System.out.println("Triangle.draw()");
}
void erase() {
System.out.println("Triangle.erase()");
}
}
public
class Shapes
{
public static Shape randShape()
{
switch((int)(Math.random() * 3)) {
default:
case 0:
return new Circle();
case 1:
return new Square();
case 2:
return new Triangle();
}
}
public static void main(String[] args) {
Shape[] s = new
Shape[9];
// 向数组里添加类型
for(int i = 0; i <
s.length; i++)
s[i] =
randShape();
// 用多态的方法调用
for(int i = 0; i <
s.length; i++)
s[i].draw();
}
} 上述源码下载
Java的多态性,有什么意义呢?它的突出优点是使程序具有良好的扩展性。它通过继承,可以派生出任意多个新类型,或向基类增加更多方法时,无须修改原有对基础类进行处理的相关程序。就是扩展性好。
我们返回再看面向对象(专指OOP)的这三个特性封装、继承、多态三者的关系。没有封装就没有继承,没有继承就没有多态。
|