В чем разница между интерфейсом и абстрактным классом? - PullRequest
1651 голосов
/ 16 декабря 2009

В чем именно разница между интерфейсом и абстрактным классом?

Ответы [ 34 ]

2138 голосов
/ 16 декабря 2009

Интерфейсы

Интерфейс - это контракт : человек, пишущий интерфейс, говорит: " эй, я принимаю вещи, выглядящие так ", а человек, использующий интерфейс, говорит " ОК, класс, который я пишу, выглядит так".

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

Например (псевдокод):

// I say all motor vehicles should look like this:
interface MotorVehicle
{
    void run();

    int getFuel();
}

// My team mate complies and writes vehicle looking that way
class Car implements MotorVehicle
{

    int fuel;

    void run()
    {
        print("Wrroooooooom");
    }


    int getFuel()
    {
        return this.fuel;
    }
}

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


Абстрактные занятия

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

Абстрактные классы очень похожи на интерфейсы, но у них есть нечто большее: вы можете определить поведение для них. Это больше о человеке, который говорит: «Эти классы должны выглядеть так, и они имеют это общее, так что заполняйте пробелы!».

Например:

// I say all motor vehicles should look like this:
abstract class MotorVehicle
{

    int fuel;

    // They ALL have fuel, so lets implement this for everybody.
    int getFuel()
    {
         return this.fuel;
    }

    // That can be very different, force them to provide their
    // own implementation.
    abstract void run();
}

// My teammate complies and writes vehicle looking that way
class Car extends MotorVehicle
{
    void run()
    {
        print("Wrroooooooom");
    }
}

Осуществление

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

В Java это правило строго соблюдается, тогда как в PHP интерфейсы являются абстрактными классами без объявленного метода.

В Python абстрактные классы - это больше трюк программирования, который вы можете получить из модуля ABC, и на самом деле он использует метаклассы и, следовательно, классы. А интерфейсы в большей степени связаны с типизацией утки на этом языке, и это смесь соглашений и специальных методов, вызывающих дескрипторы (методы __method__).

Как обычно в программировании, существует теория, практика и практика на другом языке: -)

831 голосов
/ 16 декабря 2009

Основные технические различия между абстрактным классом и интерфейсом :

  • Абстрактные классы могут иметь константы, члены, заглушки методов (методы без тела) и определенные методы , тогда как интерфейсы могут иметь только константы и заглушки методов .

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

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

  • Аналогично, интерфейс, расширяющий другой интерфейс, не отвечает за реализацию методов из родительского интерфейса. Это связано с тем, что интерфейсы не могут определять какую-либо реализацию.

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

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

131 голосов
/ 15 сентября 2013

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

enter image description here Взято из:

http://www.dotnetbull.com/2011/11/difference-between-abstract-class-and.html

http://www.dotnetbull.com/2011/11/what-is-abstract-class-in-c-net.html http://www.dotnetbull.com/2011/11/what-is-interface-in-c-net.html

78 голосов
/ 16 декабря 2009

Объяснение можно найти здесь: http://www.developer.com/lang/php/article.php/3604111/PHP-5-OOP-Interfaces-Abstract-Classes-and-the-Adapter-Pattern.htm

Абстрактный класс - это класс, который только частично реализовано программист. Может содержать один или несколько абстрактные методы. Абстрактный метод это просто определение функции, которая служит, чтобы сказать программисту, что метод должен быть реализован у ребенка класс.

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

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

38 голосов
/ 16 мая 2013

Некоторые важные отличия:

В форме таблицы:

Difference

Как заявлено Джо из javapapers :

1.Основное отличие состоит в том, что методы интерфейса Java неявно абстрактны и не могут иметь реализации. Абстрактный класс Java может есть методы экземпляра, которые реализуют поведение по умолчанию.

2. Переменные, объявленные в интерфейсе Java, по умолчанию являются окончательными. Абстрактный класс может содержать неконечные переменные.

3.Члены интерфейса Java по умолчанию являются публичными. Абстрактный класс Java может иметь обычные разновидности членов класса, такие как private, охраняемый и т. д.

4.Java-интерфейс должен быть реализован с использованием ключевого слова «Implements»; Абстрактный класс Java должен быть расширен с помощью ключевого слова «extends».

5. Интерфейс может расширять только другой интерфейс Java, абстрактный класс может расширять другой класс Java и реализовывать несколько Java интерфейсы.

6. Java-класс может реализовывать несколько интерфейсов, но он может расширять только один абстрактный класс.

7. Интерфейс абсолютно абстрактный и не может быть создан; Абстрактный класс Java также не может быть создан, но может быть вызван, если main () существует.

8. По сравнению с абстрактными классами Java, интерфейсы Java медленные, так как требуют дополнительного косвенного обращения.

37 голосов
/ 27 ноября 2015

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

Проще говоря, я хотел бы сказать:

интерфейс: Для реализации договора несколькими несвязанными объектами

абстрактный класс: Для реализации одинакового или различного поведения среди нескольких связанных объектов

Из Oracle Документация

Рассмотрите возможность использования абстрактных классов , если:

  1. Вы хотите поделиться кодом между несколькими тесно связанными классами.
  2. Вы ожидаете, что классы, расширяющие ваш абстрактный класс, имеют много общих методов или полей или требуют модификаторов доступа, отличных от public (например, protected и private).
  3. Вы хотите объявить нестатические или не финальные поля.

Рассмотрите возможность использования интерфейсов , если:

  1. Вы ожидаете, что несвязанные классы будут реализовывать ваш интерфейс. Например, многие несвязанные объекты могут реализовать интерфейс Serializable.
  2. Вы хотите указать поведение определенного типа данных, но не беспокоитесь о том, кто реализует его поведение.
  3. Вы хотите воспользоваться множественным наследованием типа.

абстрактный класс устанавливает связь "is" с конкретными классами. Интерфейс предоставляет возможность «имеет» для классов.

Если вы ищете Java в качестве языка программирования, вот еще несколько обновлений:

Java 8 в некоторой степени сократил разрыв между классами interface и abstract, предоставив функцию метода default. Интерфейс не имеет реализации для метода больше не действует.

См. Эту документацию стр. для получения более подробной информации.

Посмотрите на этот вопрос SE, чтобы примеры кода были лучше понятны.

Как мне объяснить разницу между интерфейсом и классом Abstract?

29 голосов
/ 29 сентября 2014

Суть в том, что:

  • Аннотация является объектно-ориентированной . Он предлагает основные данные, которые должен иметь «объект», и / или функции, которые он должен выполнять. Он касается основных характеристик объекта: что у него есть и что он может сделать. Следовательно, объекты, которые наследуются от одного и того же абстрактного класса, имеют общие характеристики (обобщение).
  • Интерфейс ориентирован на функциональность . Он определяет функциональные возможности, которые должен иметь объект. Независимо от того, что это за объект, пока он может выполнять эти функции, которые определены в интерфейсе, это нормально. Это игнорирует все остальное. Объект / класс может содержать несколько (групп) функциональных возможностей; следовательно, класс может реализовать несколько интерфейсов.
24 голосов
/ 09 июля 2014

Я строю здание из 300 этажей

Проект здания интерфейс

  • Например, Сервлет (I)

Здание построено до 200 этажей - частично завершено --- аннотация

  • Частичная реализация, например, универсальный и HTTP-сервлет

Строительство здания завершено - Бетон

  • Полная реализация, например, собственного сервлета

Интерфейс

  • Мы ничего не знаем о реализации, только требования. Мы можем перейти на интерфейс.
  • По умолчанию каждый метод является публичным и абстрактным
  • Это 100% чистый абстрактный класс
  • Если мы объявляем открытый, мы не можем объявить закрытый и защищенный
  • Если мы объявляем абстрактный, мы не можем объявить final, static, synchronized, strictfp и native
  • Каждый интерфейс имеет public, static и final
  • Сериализация и переходные процессы не применимы, потому что мы не можем создать экземпляр для в интерфейсе
  • Нелетучий, потому что он окончательный
  • Каждая переменная является статической
  • Когда мы объявляем переменную внутри интерфейса, нам нужно инициализировать переменные при объявлении
  • Экземпляр и статический блок не разрешены

Аннотация

  • Частичная реализация
  • У него есть абстрактный метод. Кроме того, он использует бетон
  • Нет ограничений для модификаторов методов абстрактного класса
  • Без ограничений для модификаторов переменных абстрактного класса
  • Мы не можем объявить другие модификаторы, кроме абстрактных
  • Нет ограничений на инициализацию переменных

Взято с сайта DurgaJobs

23 голосов
/ 28 мая 2012

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

Если вам нужно полиморфное поведение для классов, которые совершенно не связаны, используйте интерфейс.

18 голосов
/ 11 апреля 2012

Давайте снова поработаем над этим вопросом:

Первое, что вам нужно знать, это то, что 1/1 и 1 * 1 дают одинаковые результаты, но это не значит, что умножение и деление одинаковы. Очевидно, у них хорошие отношения, но учтите, что вы оба разные.

Укажу основные отличия, а остальное уже объяснили:

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

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...