- //形状类
- class Shape{
- public void draw(){
-
- }
- public void erase(){
-
- }
- }
- //圆类
- class Circle extends Shape{
- public void draw(){
- System.out.println("Circle.draw()");
- }
- public void erase(){
- System.out.println("Circle.erase()");
- }
- }
- //正方形类
- class Square extends Shape{
- public void draw(){
- System.out.println("Square.draw()");
- }
- public void erase(){
- System.out.println("Square.erase()");
- }
- }
- //测试类
- public class DuoTaiDemo {
- public static void main(String[] args) {
- Shape sh=new Circle();
- sh.draw();//Circle.draw()
- sh.erase();//Circle.erase()
- }
- }
复制代码 上面的程序,有个形状的父类,圆类和正方形类继承了形状这个类。在测试类中,创建了一个Circle对象,并把得到的引用值给了sh,但是,大家没有迷惑吗?程序怎么就知道,我是调用的Circle类中的方法,而不是Square类中的方法吗?这就要谈一谈绑定的话题了。
将一个方法调用同一个方法主体关联起来就被称作是绑定,通俗的说就是在程序执行之前的编译期就绑定类型。若在程序之前绑定就是前期绑定,例如我们熟悉的C语言就是前期绑定的。那么对应着前期绑定就会有后期绑定,也叫做动态绑定或者运行时绑定。
在Java语言中,除了static方法和final方法(private方法属于final方法),其余都是后期绑定的,这就是为什么静态代码块会随着类的加载而加载的深层次原因。现在回到刚开始的问题,如果我们用前期绑定的思维看,就会让人迷惑,只有一个Shape引用时,它到底该调用哪个方法了?这就的后期绑定来帮忙,使得在运行的时候才能够判断对象的类型,从而调用恰当的方法。换句话说,就是编译期刚开始不知道对象的类型,但是方法调用机制能找到正确的方法体,并加以调用。所以,在编译时,编译期不需要获得任何特殊信息就能进行正确的调用,对draw()方法的正确调用就是通过后期绑定进行的。
最终的结论就是,多态就是后期绑定的另外一个说法,这就是多态最深层次的分析,多态依赖着后期绑定,后期绑定也运用在多态上,天作之合。
|
|