есть интерфейс и класс его реализующий, создаем объект, помещаем ссылку в переменную типа интерфейса. Через переменную - ссылку типа интерфейса нельзя обратится к методам класса которых нет в интерфейсе?
hidden #2158068
25 уровень
по теории вопрос
Обсуждается
Комментарии (6)
- популярные
- новые
- старые
Для того, чтобы оставить комментарий Вы должны авторизоваться
JustinianJudge в Mega City OneMaster
20 марта 2020, 21:31полезный
Тип переменной определяет набор методов и полей класса, к которым можно обращаться.
Если в переменной лежит экземпляр класса, который имеет более расширенную функциональность, то обратиться к его членам (методам и переменным) мы можем сделав операцию приведения к нужному типу (сужение к определенному типу).
Например:
или чтобы было понятней в несколько строк:
Но сужение типа и проверки через instance of и getClass() cчитаются не очень хорошей практикой, поскольку эти операции небезопасны, поскольку ошибки будут вылезать в рантайме, а чем позже выявляется ошибка, тем больше сложность и стоимость ее исправления.
Мы таким образом уходим от использования преимущества строгой типизации джавы, когда компилятор на страже нашего кода, ведь компилятор такое пропустит:
Не всегда такого удается избегать, но нужно держать в голове и стараться делать дизайн программы таким, чтобы этого не было или было поменьше.
А так, правило гласит, что не имея иных явных требований, мы по умолчанию объявляем переменную именно по супертипу - интерфейсу или классу родителю, для использования преимуществ полиморфизма.
Особенно это касается коллекций:
Если мы знаем, что нам нужна функциональность именно самого класса, тогда используем тип переменной сам класс.
Если приходится использовать тип самого класса, а не родителя, часто это говорит, что в ООП дизайне, что-то не так.
Но это отдельная большая тема
+2
hidden #2244663Expert
20 марта 2020, 21:14полезный
Протестил сейчас для полной уверенности. Нет, нельзя.
Если ваша переменная имеет тип интерфейса, а на класса, то вызывать можно только методы интерфейса, что и логично.
НО! Можно переменную скастовать к типу класса, который имплементирует интерфейс. И тогда все получится.
+1
hidden #2244663Expert
20 марта 2020, 21:17
Например
0
Ksenia VolkovaJava Developer в DXCMaster
20 марта 2020, 21:18полезный
И это касается не только интерфейсов. При наследовании то же самое.
+1
hidden #2244663Expert
20 марта 2020, 21:19
Что, опять же, логично. Вообще, хороший вопрос. Не задумывался об этом.
0
Ksenia VolkovaJava Developer в DXCMaster
20 марта 2020, 21:10полезный
Нельзя.
У переменной типа X можно вызвать только методы, которые есть в X
+1