Основы объектно-ориентированного проектирования


Как не следует использовать наследование - часть 2


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

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

Рисунок Джеффа Хокинга (голова его похожа на его же авто с открытыми дверцами)

Рис. 6.2.  Рисунок Джеффа Хокинга (голова его похожа на его же авто с открытыми дверцами)

Наследование не является тривиальной концепцией, так что мы можем забыть и простить автора процитированного отрывка, но сам пример имеет важную практическую пользу - он помог нам стать немного умнее и напомнил базисное правило наследования:

Правило: Наследование "Is-a" (является)

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

Другими словами, мы должны быть способными убеждать, что каждый B is an A (отсюда имя: "is-a").

Вопреки первому впечатлению, это слабое, а не строгое правило, и вот почему:

  • Обратите внимание на фразу "привести аргументы". Мы не требуем доказательства того, что каждый B всегда является A. В большинстве случаев мы оставляем пространство для дискуссии. Верно ли, что каждый "сберегательный счет" (savings account) является "текущим счетом" (checking account)? Здесь нет абсолютного ответа - все зависит от политики банка и вашего анализа свойств различных видов счетов. Возможно, вы решите сделать класс SAVINGS_ ACCOUNT наследником BANK_ACCOUNT или поместить его где-либо еще в структуре наследования. Разумные люди могут все же не согласиться с результатом. Это нестрашно, важно лишь, чтобы был случай, для которого ваши аргументы способны устоять. В нашем контрпримере: нет ситуации, при которой аргументы в пользу того, что CAR_OWNER является CAR, могли бы устоять.
  • Наш взгляд на то, что означает отношение "является", будет довольно либеральным.Он не будет, например, препятствовать наследованию реализации - форме наследования, многими считающейся подозрительной.

Эти наблюдения показывают как полезность, так и ограниченность правила "Is-a". Оно полезно как отрицательное правило, позволяя обнаружить и отвергнуть неподходящее использование наследования. Но как положительное правило оно недостаточно - не все, что проходит тест, заданный правилом, является подходящим случаем наследования.




Начало  Назад  Вперед