Одним из принципов SOLID является инверсия зависимостей (dip). В литературе по программированию и в интернете масса источников с детальным описанием этого принципа. И большинство кандидатов на собеседовании успешно отвечают заученными фразами на вопрос: "Что такое инверсия зависимости?". Но при практической реализации мгновенно возникает вопрос, а в чем же собственно заключается инверсия и как она программируется? Далее будет рассмотрен данный принцип более подробно.
Прямой ход зависимости
Сделаем небольшое отступление к истокам программирования. Самые первые программы, до появления полиморфизма и объектно-ориентированного подхода, выглядели примерно следующим образом.
Зависимости были направлены в одном направлении. Но возникает проблема, и не одна.
Controller зависит от деталей реализации - методов calculateFulltimeSalary() и caclculatePartialTimeSalary().
Нетрудно догадаться, что при добавлении нового типа работника нужно будет редактировать объект Controller.
При добавлении очередного метода в Controller он быстро разрастется до небывалых размеров.
Поэтому в программе стали оделять те части, которые зависят от аппаратуры, данных, и т.п. Таким образом, скажем, при появлении нового принтера, достаточно было запрограммировать его управление (драйвер), а логика по подготовке документа для печати оставалась неизменной.
Инверсия зависимости
С появлением объектно-ориентированного подхода и полиморфизма стало возможным скрывать реализацию метода за интерфейсом класса. Именно поэтому в одном из самых популярных источников сказано, что классы должны зависеть от абстракций, а не от конкретных деталей [1], что привело примерно к следующей картине.
На схеме отражена суть инверсии - в какой-то момент времени стрелка зависимости становится направлена в обратном направлении.
Полиморфизм и ООО выходят за рамки данной статьи и обсуждаться не будут.
Заключение
Выучить наизусть фразу из любого источника по программированию и успешно пройти собеседование еще не означает наличие знания и понимания техники программирования. Более того, удивляет наличие огромного количества статей, которые не могут в краткой и ясной форме объяснить суть пятого из принципов SOLID [2]. Целью этой статьи была передача опыта и, что более важно, желание находится в среде образованных профессионалов, а не дилетантов.
Более того, вы всегда можете перейти к первой в поиске статье на эту тему [3].
Список источников
Комментарии (8)
dopusteam
19.12.2022 20:33+4Схема сильно упрощена, но в ней отражена суть инверсии - в какой-то момент времени стрелка становится направлена в обратном направлении
Объяснение от бога, конечно
AceRodstin Автор
19.12.2022 21:05-4Написано в стиле источника [1]. Кратко и по-сути.
С той лишь разницей, что показано, **где возникает инверсия**.
lair
19.12.2022 21:59+4В ваших диаграммах даже не понятно, что обозначает стрелочка. Что уж говорить о том, каким же волшебством она разворачивается?
manyakRus
20.12.2022 13:30Работник должен сам себе зарплату рассчитывать ?
На первой схеме: Работник обращается - в отдел бухгалтерии - бухгалтеры заходят в программу 1С и расситывают зарплату.
На второй схеме: Работник обращается - в отдел бухгалтерии - бухгалтеры говорят: посчитайте себе зарплату сами :-)т.е. первая схема лучше :-)
gdt
20.12.2022 19:59Есть же примеры получше. Например, надо писать логи, для этого есть какой-то ConsoleLogger, мы его у себя используем - т е зависим от него. Применяя этот принцип, выделяем интерфейс ILogger, и теперь мы не зависим от конкретного логгера, а наоборот - логгер зависит от нас (при условии что интерфейс определен например в том же модуле что и потребитель, а конкретный логгер - в другом модуле).
lamerok
Главное, что про С++, ведь инверсия зависимостей она только там.