ЖУРНАЛ СТА №3/2023

Абстракция Абстракция – это модель, содержа- щая только существенные характери- стики для решения поставленной зада- чи. Выбранная абстракция определяет интерфейс, посредством которого с ней осуществляется взаимодействие. Ин- терфейс связан с набором обязательств, которые необходимо выполнять, чтобы обеспечить поддержание выбранной абстракции. Потенциальное множество всех объ- ектов с одинаковыми характеристика- ми образуют класс . Отсюда следует, что классов существенно меньше, чем объ- ектов. Поэтому при проектировании лучше описать сразу весь класс, а по- том использовать объекты как экзем- пляры этого класса. У класса есть атри- буты (свойства) и методы . Атрибуты описывают состояние объекта, а мето- ды – операции, которые может выпол- нять объект. Совокупность методов и их обязательств определяет поведение объекта. Открытые (доступные снару- жи объекта) атрибуты и методы обра- зуют интерфейс. Класс и тип объекта при определённых условиях можно считать синонимами [2]. В нашем примере OPC-сервер должен предоставить простую абстракцию OPC-клиенту для взаимодействия с ко- тельным оборудованием. Пусть этой абстракцией будет котёл. Для этого определим класс Boiler (см. UML-диа- грамму на рис. 1). Назначение котла – нагрев воды, поэтому существенной характеристикой является температу- ра воды на выходе котла. Для этого определим атрибут outWaterTemp типа Double , который будет предоставлять текущее значение температуры в виде вещественного числа. Данный атрибут доступен для OPC-клиента (открытые члены класса обозначаются знаком +), но предназначен только для чтения (в фигурных скобках указано это огра- ничение). Также для работы с котлом необходи- мо знать его состояние (остановлен, ра- ботает, запускается, неисправен и т.д.). Для этого определим атрибут status ти- па Int16 , предназначенный только для чтения (OPC-клиент не может изменять его значение). Статус котла будет коди- роваться целым числом, сами коды по- ка неизвестны. Простой абстракцией для управления котлом является набор из двух команд: запустить и остановить нагрев. Для это- го определим методы startHeating() и stopHeating() соответственно. Эти мето- ды не имеют параметров и ничего не возвращают. Названия методов выде- лены курсивом – это означает, что они абстрактные, т.е. не имеют реализации, так как на данном этапе проектирова- ния ещё неизвестно, как именно запус- кать и останавливать котёл. Таким образом, класс Boiler задаёт простой интерфейс для работы с аб- страктным котлом. Название класса Boiler также выделено курсивом – это означает, что класс абстрактный, т.е. невозможно создать экземпляры этого класса, так как не спроектированы мно- гие вещи, и использовать такой объект пока нельзя. Предложенная абстракция фокусиру- ет разработку только на существенных характеристиках, устраняя всё лишнее. В итоге это упрощает и процесс про- ектирования, и полученный результат. Иерархия Иерархия используется для упоря- дочивания абстракций по уровням [2]. Рассмотрим два механизма, порождаю- щих иерархию: наследование и компо- зиция . Наследование – заимствование клас- сом не скрытых атрибутов и методов у другого класса. Класс, который насле- дует, является дочерним . Класс, от ко- торого наследуют, является родитель- ским . Наследование порождает иерар- хию классов с отношением «обобще- ние-специализация». Дочерний класс является специализацией родитель- ского, и наоборот, родительский класс является обобщением дочернего. Композиция – объединение частей. Композиция порождает иерархию объ- ектов с отношением «часть-целое». Ком- понентные объекты являются частями композиционного (целого) объекта. В нашем примере оборудование мо- жет меняться – проработаем его воз- можные специализации и организуем это в иерархии классов. Допустим, котёл может быть с электрическим или газо- вым нагревом. Для этого определим два класса: ElectricBoiler и GasBoiler соответ- ственно. Оба класса наследуют атрибуты и методы родительского класса Boiler (родительский класс указывают стрел- кой на UML-диаграмме). Кроме того, в классах указана их специализация: электрический котёл имеет нагреватель (атрибут heater типа ElectricHeater ), а газовый котёл – газовую горелку (атри- бут burner типа GasBurner ). Класс Gas- Boiler задаёт иерархию объектов: горелка (объект burner ) является частью газового котла (объекта класса GasBoiler ). Класс GasBurner определяет абстракт- ную газовую горелку и является корнем уже другой иерархии классов (см. UML- диаграмму на рис. 2). Абстрактная горел- ка позволяет подать искру для розжига – для этого атрибут spark типа Boolean нуж- но установить в True . Также горелка име- ет датчик наличия пламени (атрибут flame типа Boolean только для чтения). По способу подачи воздуха горелки могут быть атмосферными или наддув- ными – этому соответствуют два дочер- них класса AtmoGasBurner и AirBoost- GasBurner соответственно. Для подачи газа атмосферная горелка имеет газовый СТА 3/2023 54 www.cta.ru НОУ - ХАУ Рис. 1. UML-диаграмма классов котлов

RkJQdWJsaXNoZXIy MTQ4NjUy