Подтвердить что ты не робот

Если вы переписываете поле в подклассе класса, подкласс имеет два поля с тем же именем (и другого типа)?

У меня есть 3 класса:

public class Alpha {
    public Number number;
}

public class Beta extends Alpha {
    public String number;
}

public class Gama extends Beta {
    public int number;
}

Почему выполняется компиляция следующего кода? И почему тест проходит без каких-либо ошибок времени выполнения?

@Test
public void test() {
    final Beta a = new Gama();
    a.number = "its a string";
    ((Alpha) a).number = 13;
    ((Gama) a).number = 42;

    assertEquals("its a string", a.number);
    assertEquals(13, ((Alpha) a).number);
    assertEquals(42, ((Gama) a).number);
}
4b9b3361

Ответ 1

Переменные-члены нельзя переопределять как методы. Переменные number в ваших классах Beta и Gama скрывают (не переопределяют) переменную-член number суперкласса.

Вы можете получить доступ к скрытому члену в суперклассе.

Ответ 2

Поля не могут быть переопределены; во-первых, они не имеют доступа к полиморфизму: вы просто объявляете новое поле в каждом случае.

Он компилируется, потому что в каждом случае тип выражения для компиляции достаточно для определения того, какое поле называется number.

В реальном программировании вы избегаете этого двумя способами:

  • Здравый смысл: поля затенения делают ваш код более трудным для чтения, поэтому просто не делайте этого.
  • Видимость: если вы сделаете все свои поля частными, подклассы не будут знать о них в любом случае