Когда внедрять и расширять? [закрыто]

90
  • Когда следует implementили extendиспользовать?
  • Какие есть примеры из реального мира?

Это правильно?

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

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

Расширяющиеся классы заставляют расширенный (дочерний?) Класс наследовать все от своего родительского класса, кроме методов и переменных, объявленных как private?

Ожидаемый сценарий из реальной жизни: у меня есть один вызываемый класс sessionsс двумя дочерними классами с именами sessioncookiesи databasesessions. sessioncookiesи databasesessionsвместе наследуют ряд взаимных параметров конфигурации от своих родительских сеансов, что упрощает изменение параметра конфигурации, чтобы повлиять на все виды возможного хранилища данных посетителей.

Промышленное
источник
1
Я рекомендую вам прочитать о наследовании.
Rafe Kettler

Ответы:

64

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

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

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

Наследование - это большая концепция в ООП, которая выходит далеко за рамки PHP. Я рекомендую вам прочитать статью в Википедии о наследовании и, возможно, шаблонах проектирования от банды четырех .

Я считаю, что ваше понимание наследования в основном правильное. Следующим шагом будет его использование в производстве.

Рэйф Кеттлер
источник
4
Многие сейчас считают книгу «Банда четырех» слишком тяжелой с точки зрения материала как введения в шаблоны проектирования. Популярной альтернативой является Head First: Design Patterns, которая облегчает чтение. amazon.co.uk/Head-First-Design-Patterns-Freeman/dp/0596007124
Bendihossan
1
«Следите за случаями, когда вы определяете одни и те же методы в нескольких классах; это отличные случаи, когда вы можете выделить эти методы в базовый класс». Будет ли расширение класса иметь преимущество перед использованием трейта для определения этих методов?
Даниэль Вайнер
1
«Наследование полезно для уменьшения объема кода, который вы переписываете» - цель наследования - разделить поведение, а не код. По возможности, черты - это способ совместного использования кода, а не расширения абстрактного класса конкретными классами, которые в остальном не имеют ничего общего. Обычно вы также можете моделировать свои классы как отношения типа «есть-а», а не как-есть, что еще больше облегчит повторное использование кода и полиморфизм.
Дункан
12

Осуществлять:

Интерфейсы - это абстрактные классы, поэтому вы можете только объявлять вещи. Класс реализует интерфейс. Вы можете реализовать несколько интерфейсов.

Расширить:

Вы расширяете классы, когда вам нужна более конкретная версия класса.

Пример:

// Contract: a pet should play
public interface Pet {
    public void play(); 
}

// An animal eats and sleeps
class Animal {
    public void eat();
    public void sleep();
}


public class Camel extends Animal {

}

public class Dog extends Animal implements Pet {    
    public void play() {...}
}

И Верблюд, и Собака - животные, поэтому они расширяют Animalкласс. Но только собака является специфическим видом из Animalчто также может бытьPet

Ахмад Мобараки
источник