2015-05-02 3 views
5

В Java 8 представлены стандартные и статические методы на интерфейсах. Итак, теперь у вас могут быть конкретные реализации в вашем интерфейсе, независимо от того, используются ли они по умолчанию или статические методы.Причина добавления стандартных и статических методов в интерфейсы

Причина, по которой Java заявила о добавлении этих двух новых методов, - «обеспечить двоичную совместимость с кодом, написанным для более старых версий этих интерфейсов».

Мой вопрос:

  • Почему искажать интерфейс оригинальную концепцию, предполагают, чтобы быть полностью абстрактным, чтобы поддержать существующие архитектурные проблемы?
  • В чем разница между использованием абстрактного класса и новой версии интерфейса, отличной от способности класса расширять несколько интерфейсов?
+2

Возможный дубликат http://stackoverflow.com/questions/22591499/what-are-the-differences-between-abstract-classes-and-interfaces-in-java-8 – Vulcan

+0

@ Vulcan мой вопрос нацелен на использование обновлений java 8, а не разница между абстрактным и интерфейсом –

ответ

7

Причина, по которой java заявила, что добавляет эти два новых метода, «обеспечивает двоичную совместимость с кодом, написанным для более старых версий этих интерфейсов».

Это относится только к методам по умолчанию (не статическим методам) и опускает какой-либо контекст. От Goetz, State of the Lambda

Назначение методов по умолчанию ... заключается в том, чтобы позволить интерфейсам развиваться совместимым образом после их первоначальной публикации.

Основная цель состоит в том, чтобы позволить эволюцию интерфейса, то есть, добавление новых методов. Если к интерфейсу добавлен новый метод, существующим классам, реализующим интерфейс, будет недоставать реализации, что было бы несовместимо. Чтобы быть совместимым, реализация должна произойти откуда-то, поэтому она предоставляется по умолчанию.

Зачем искажать интерфейс оригинальной концепции, которая должна быть полностью абстрактной, чтобы поддерживать существующие архитектурные проблемы?

Основная цель интерфейса Java - specify a contract, которую может реализовать любой класс без необходимости изменять свою позицию в иерархии классов. Верно, что до Java 8 интерфейсы были чисто абстрактными.Однако это не является существенным свойством интерфейсов. Даже когда включены методы по умолчанию, интерфейс в его сердце все еще указывает контракт на класс реализации. Класс реализации может переопределять методы по умолчанию, поэтому класс по-прежнему полностью контролирует его реализацию. (Заметим также, что default methods cannot be final.)

В чем разница между использованием абстрактного класса и новую версию интерфейса, кроме способности класса, чтобы расширить несколько интерфейсов?

Способность класса расширять несколько интерфейсов тесно связана с другим различием между интерфейсами и абстрактными классами, а именно, что интерфейсы не могут содержать состояние. Это основная трудность при разрешении множественного наследования: если суперкласс должен появляться несколько раз в родословной класса, будет ли состояние суперкласса появляться только один или несколько раз? (Это так называемая проблема с алмазами.)

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

(В Java 9, поддержка частных методов была добавлена. Это полезно для совместного осуществления среди стандартных или статических методов интерфейса.)

Наконец, статические методы в интерфейсах не влияют на наследование классов, и они не являются частью контракта с интерфейсом. Это всего лишь способ организации полезных методов более удобным способом. Например, обычное использование статических методов в интерфейсе для статических заводских методов. Если статические методы не допускались в интерфейсах, статические методы фабрики должны были бы быть помещены в класс компаньона. Разрешение статических методов в интерфейсах позволяет группировать такие методы с самим интерфейсом, когда это необходимо.

2

Проблема заключается в том, что вы никогда не сможете расширить интерфейс с помощью нового метода без нарушения совместимости. Существующие классы не будут реализовывать этот метод и поэтому не будут работать с новой версией кода, который использует этот метод.

Это была серьезная проблема для самой библиотеки классов Java, поскольку она не может добавлять часто задаваемые методы в базовые интерфейсы (например, коллекции). Это был основной драйвер для реализации стандартных методов для интерфейсов.

Разница между этим новым методом и использованием абстрактного класса (который является довольно хорошим шаблоном для этой проблемы в некоторых случаях) заключается в том, что вы не можете наследовать от нескольких абстрактных классов. Но вы можете легко реализовать несколько интерфейсов.

Статические методы в интерфейсах менее ясны, я думаю, что они здесь, чтобы помочь вам реализовать методы по умолчанию (если два метода по умолчанию имеют одинаковый код, оба они могут вызвать статический метод).

Смежные вопросы