Страницы

Поиск по вопросам

вторник, 9 октября 2018 г.

Получение ссылки на экземпляр суперкласса

Пытаюсь разбираться с наследованием в Java. Есть некоторый код:
class A { A getThis() { System.out.println("call getThis() from A"); return this; //(3) } //(3)
Object getSuper() { System.out.println("call getSuper() from A"); return null;} }
class B extends A { B getThis() { System.out.println("call getThis() from B"); return this; }
A getSuper() { System.out.println("call getSuper() from B"); return super.getThis(); } }
class Tester { public static void main (String[] args) { Object a = new B().getSuper(); //(1) System.out.println(a); a = new B().getSuper().getSuper(); //(2) System.out.println(a); } }
В результате на консоль выводится следующий текст:
call getSuper() from B call getThis() from A B@25154f call getSuper() from B call getThis() from A call getSuper() from B call getThis() from A B@10dea4e
Я ожидал, что при отработке строки (1) в a будет лежать экземпляр класса A, а после отработки строки (2) в a будет лежать null. Почему в результате возврата this из строки (3) возвращается ссылка не на родительский класс, а на исходный?

Как я понимаю, при создании экземпляра класса B, в нём хранится ссылка на экземпляр родительского класса A. Я вижу косвенное подтверждение своих слов:
При вызове конструктора класса B происходит вызов конструктора класса A. Даже при переопределении метода f в классе B можно добраться до метода f класса A через конструкцию super.f() Несмотря на это, при работе с экземпляром класса B, я не вижу способа вернуть из него ссылку на экземпляр класса A, который используется в нём. Есть ли какой-то способ всё же реализовать такую возможность?


Ответ

Мне кажется вы путаете понятия Класс и объект.
Класс – это способ описания сущности, определяющий состояние и поведение, зависящее от этого состояния, а также правила для взаимодействия с данной сущностью (контракт).
Объект (экземпляр) – это отдельный представитель класса, имеющий конкретное состояние и поведение, полностью определяемое классом.
Ключевое слово this указывает не на класс, а на экземпляр класса (объект). Ключевое слово super обеспечивает доступ к свойствам и методам этого же объекта но описанным в суперклассе.
Например: Вы создали объект бирюса класса Холодильник, а класс Холодильник наследуется от класса БытоваяТехника. Объект бирюса является и холодильником, и бытовой техникой. this вернет ссылку на объект бирюса, не важно через какой класс получена ссылка Холодильник или БытоваяТехника, объект от этого не меняется.
Так и у вас объект a является экземпляром класса B, одновременно является экземпляром класса А, так как от него наследуется. Когда Вы вызываете метод getSuper() по цепочке в итоге возвращается this, то есть ссылка на объект a
Определения класса и объекта взяты отсюда

Комментариев нет:

Отправить комментарий