【问题标题】:how overriding works in the following code?以下代码中的覆盖如何工作?
【发布时间】:2014-01-08 21:13:53
【问题描述】:

考虑下面的java代码:

public class Superclass {    
    public void printMethod() {
        System.out.println("Printed in Superclass.");
    }
}

这是一个子类,称为 Subclass,它覆盖了 printMethod():

public class Subclass extends Superclass {    
    // overrides printMethod in Superclass
    public void printMethod() {
        super.printMethod();
        System.out.println("Printed in Subclass");
    }
    public static void main(String[] args) {
        Subclass s = new Subclass();
        s.printMethod();    
    }
}

得到的输出如下:

Printed in Superclass
Printed in Subclass

如果子类被覆盖,为什么超类println 仍然显示在屏幕上? 不只是在子类上显示方法的内容吗?

如果方法被覆盖,为什么在下面的代码中不调用 super?

@Override
public boolean onCreateOptionsMenu(Menu menu) {
    // Inflate the menu; this adds items to the action bar if it is present.
    getMenuInflater().inflate(R.menu.main, menu);
    return true;
}

【问题讨论】:

  • 你认为super.printMethod(); 会做什么?

标签: java


【解决方案1】:

1因为方法super.printMethod();的第一行

2因为没有调用super 方法。

【讨论】:

    【解决方案2】:
    • 如果子类被覆盖,为什么超类 println 仍然显示在屏幕上?

      因为你打电话给super.printMethod()。这调用了printMethod() 的父类实现。

    • 如果方法被覆盖,为什么在下面的代码中没有调用 super?

      因为开发人员不需要或不希望父类中的代码执行 - 他想完全重写该方法。您可能还会看到在未定义父实现时使用override 关键字,例如使用接口或抽象类。

      不需要调用方法的父类实现。

    【讨论】:

      【解决方案3】:

      如果子类被覆盖,为什么超类 println 仍然存在 显示在屏幕上?它不只是假设显示的内容 子类的方法?

      这一行:

      super.printMethod();
      

      将调用super 类的printMethod()。这基本上会变成:

      new Superclass().printmethod();
      

      您不需要调用 super 来进行覆盖。改为这样做:

      // overrides printMethod in Superclass
      public void printMethod() {
          //super.printMethod();
          System.out.println("Printed in Subclass");
      }
      

      解决您的问题的另一种方法是执行以下操作:

      public class Superclass {    
          public void printMethod() {
              System.out.println("Printed in " + this.getClass().getName() + ".");
          }
      }
      

      那就这样吧:

      public class Subclass extends Superclass {    
          // overrides printMethod in Superclass
          public void printMethod() {
              super.printMethod();//just do override
          }
          public static void main(String[] args) {
              Subclass s = new Subclass();
              s.printMethod();    
          }
      }
      

      另一个问题,为什么在下面的代码中没有调用 super 如果方法被覆盖?

      如上所述,您不需要super 来执行@Override。来自this question

      每次重写方法时使用它有两个好处。这样做 您可以利用编译器检查来确保您 当您认为自己是时,实际上正在覆盖一种方法。这样,如果 你犯了一个常见的错误拼写方法名称 正确匹配参数,您将被警告您的方法 实际上并没有像您认为的那样覆盖。其次,它使 您的代码更容易理解,因为方法更明显 被覆盖。

      此外,在 Java 1.6 中,您可以使用它来标记方法何时 实现一个接口以获得相同的好处。我想会是 最好有一个单独的注释(如@Implements),但它 总比没有好。

      如果您想了解更多关于何时将super方法覆盖 一起使用,那么check this article question.

      【讨论】:

      • 如果我理解正确,如果你删除了 super 那么你就没有调用 super 的 printMethod();对?那么为什么在这种情况下覆盖有用呢?我可以创建 2 个不扩展任何东西的类,它们都有一个打印语句。
      • 根据您的设计,覆盖方法很有用。我已经更新了你为什么使用@Override的答案。
      • @user3170491 你还不了解 OOP,是吗?答案是多态性。对于简单的程序,当然可以。但在更高层次上,组织代码以适应接口是有益的,这样它就可以是多功能和模块化的。
      【解决方案4】:

      您不必使用super.printMethod(); 调用超类方法来覆盖该方法,但是您这样做了,所以

      Printed in Superclass
      

      已打印。要不打印,请删除对super.printMethod(); 的调用;没必要。

      对于onCreateOptionsMenu,它没有使用被覆盖的功能,所以不需要调用super.onCreateOptionsMenu

      【讨论】:

        【解决方案5】:

        当你调用 super() 时,你调用了超类的方法。如果您只是删除了 super() 调用,则覆盖仍然可以在不打印“在超类中打印”的情况下工作。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2013-11-04
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多