zoukankan      html  css  js  c++  java
  • 一个Java的小问题

      老师今天在讨论群里抛出了一个问题,让大家尝试思考一下他所给的一段代码输出是什么。

      其代码如下:

      

    class T {
        void foo() { this.bar(); }
        void bar() { System.out.println("T.bar"); }
        public static void main(String args[]) {
            B b = new B();
            b.foo();
        }
    }
    
    class B extends T {
        void foo() { super.foo(); }
        void bar() { System.out.println("B.bar"); }
    }

      思考了一波:

        实例化子类对象,子类父类都没有显式构造器,就是在子类父类方法之间跳来跳去的。

      “嗯,答案一定是'T.bar'”。

      但还是敲了一遍,发现答案竟然是'B.bar'......(如图)

      室友说:“对啊,this不就是指向当前对象嘛...”

      (啪,打脸...疼...)

      重新审视了一遍,才发现自己对于this还是没理解到位...

      也就是说,整段代码执行流程如图:

      问题就在于this.bar()的指向问题... 平时一般遇到this一般都会在本类里(这里就是T类)去找是否有将之实现的方法,若有,就是它了。

      但是这次不同,事实上,正是this,使得当前方法指向其具体的对象,当这个对象实现了这个方法(这里的B类里将bar()方法覆盖了),自然this.bar()就会指向子类实现的这个bar()方法。

      本质上,输出B.bar是方法覆盖的问题,但自己犯错的原因是this的指向问题。

      因此,当我们稍微改一下代码。

      将B类的bar方法注释掉,让其不能覆盖其父类T的bar方法,结果this依旧是指向B类对象,但要调用bar方法时,发现B类没有bar方法的实现,因此“追溯”到B的父类中去寻找bar方法,此时找到了父类的bar方法并将其调用,输出自然也就是T.bar(如图)。

      

      此时,再来看另一种改动:只是在父类T中删掉了this,运行结果如图:

      可以看到,程序的输出结果依旧是B.bar。(这或多或少超出了我的预料)

      也就是说,这时的程序,和含有this关键字时,是一样的......

      这道题给我的印象还是很深刻的,毕竟自己看完题之后,竟然一点儿都不谦虚地直接喊出了一个错误答案...

      以后一定会多多注意this和super这样的很容易“改变”程序流程的关键字...

  • 相关阅读:
    基于摸板匹配的目標跟蹤算法
    spoj 2713 Can you answer these queries IV
    zoj 3633 Alice's present
    hdu 3642 Get The Treasury
    poj 1195 Mobile phones
    poj 2760 End of Windless Days
    zoj 3540 Adding New Machine
    spoj 1716 Can you answer these queries III
    spoj 1043 Can you answer these queries I
    spoj 2916 Can you answer these queries V
  • 原文地址:https://www.cnblogs.com/stevenshen123/p/8625326.html
Copyright © 2011-2022 走看看