Java: Являются ли this.foo() и super.foo() одинаковыми, когда foo() находится в суперклассе?

Скажем, у меня есть следующие классы:

class Foo {
    protected void method() {}
}

class Bar extends Foo {

}

На данный момент из класса Bar у меня есть доступ к method() двумя способами:

  • super.method();
  • this.method();

Из того, что я вижу, они, похоже, выполняют одно и то же действие. Есть ли разница между этими двумя в этом контексте? Есть ли предпочтительная версия для использования, если это так?

Использование super имеет смысл, потому что method() является частью суперкласса. Использование this тоже имеет смысл, так как Bar наследует свойства класса Foo и, следовательно, method(), верно?

Ответ 1

Да, this.foo() вызывает тот же метод, что и super.foo().

Обратите внимание, что будет разница, если foo() переопределено в дочернем классе. Но в этом случае он выполняет ту же самую реализацию метода.

Мы используем super.foo() когда нам нужно специально запросить выполнение реализации суперкласса, когда в текущем классе есть один.

Использование супер имеет смысл, потому что метод() является частью суперкласса

Да, но помните, что дочерний класс может измениться в какой-то момент и получить переопределенное foo(), и в этом случае super.foo() может начать называть непреднамеренную реализацию.
Это то, о чем нужно знать. По этой причине вызов this.foo() или unqualified foo() может быть оправдан.

Ответ 2

Просто имейте в виду, что ребенка можно переопределить еще раз:

public class Main {
  static class Foo {
    protected void method() {
      System.out.println("Bye");
    }
  }

  static class Bar extends Foo {
    {
      this.method();
      super.method();
    }
  }

  static class Baz extends Bar {
    protected void method() {
      System.out.println("Hi");
    }
  }

  public static void main(String[] args) {
    new Baz();
  }
}

Производит:

Hi
Bye

Таким образом, хотя this.method() и super.method() могут вести себя одинаково в некоторых случаях, они не создают одинаковый байт-код.