Codesys. Объектно-ориентированное программирование на ПЛК. Часть 5. Принцип открытости/закрытости.

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

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

На этот раз мы попытаемся понять принцип открытости/закрытости, который звучит как:

Программные сущности должны быть открыты для расширения и закрыты
для изменения

Вот мы и познакомились с этим принципом всем спасибо…. хотелось бы мне сказать, но…

Как понимать.

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

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

Есть два типа возможной реализации, один через наследования, когда новый код наследуется от старого при этом есть возможность изменения интерфейса реализации. Второй — это полиморфизм. Когда новая программная сущность реализует интерфейс старой программной сущности, при этом может частично вызывать функционал старой сущности.

Синтетический пример

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

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

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

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

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

Как же такого избежать? Интерфейсы!

Теперь как бы мы не меняли наши UNITы, они все реализует интерфейс с двумя методами, которые требуются для работы нашего функционального блока.

Всем спасибо. Вопросы, задачки и прочее присылайте на почту. Регулярные новости в ТГканале

Ответить