UML (Unified Modeling Language – унифицированный язык моделирования) является языком графического описания для объектного моделирования при разработке программного обеспечения.
Язык UML был разработан как унификация множества нотаций, которые использовались для графического описания объектно-ориентированных систем. Предложен Гради Буч, Джеймс Рамбо и Айвар Якобсон. Позже к разработке UML присоединилось множество компаний. В данный момент UML 1.4.2 принят в качестве международного стандарта. Текущая версия - UML 2.
UML описывает системы с помощью набора диаграмм. Каждая такая диаграмма является взглядом «со своей стороны» на систему.
Диаграмма прецедентов (Use case diagram)
Диаграмма прецедентов представляет различные сущности, которые взаимодействуют с системой (пользователей, внешние устройства и другие программные системы) и указывают функции, которые необходимо реализовать в программной системе.
Актёр (actor) инициирует прецедент (use case). Прецедент описывает последовательность взаимодействий между актёром и системой. Актёр изображается на диаграмме в виде фигуры человечка, система – в виде прямоугольника, прецедент – в виде эллипса внутри этого прямоугольника.
На рисунке показаны два пользователя системы (студент и преподаватель) и прецеденты взаимодействия с системой тестирования знаний – выбор предметной области, выбор вопросов и ответы на вопросы. Связи позволяют указать, какой из актёров вызывает прецеденты.
Диаграмма прецедентов служит для описания группы действий, которые инициируются конкретным лицом. Таким образом её основное назначение – упрощения взаимодействия с пользователями. Диаграмма прецедентов описывает, что система должна делать и как это будет выглядеть для пользователя.
Актёры представляют собой не физических людей, а их роли. Это означает, что когда человек взаимодействует с системой различными способами (предполагая различные роли), он отображается несколькими актёрами.
Диаграмма классов (Class diagram)
Классы и объекты отображаются в UML прямоугольниками. В прямоугольнике класса всегда вписывается имя класса. Дополнительно могут быть указаны атрибуты и методы операции. Когда присутствуют все три элемента, то в верхней секции прямоугольника находится имя класса, в средней – атрибуты, а в нижней – операции.
Для обозначения квалификаторов доступа используются префиксы перед именами методов и членов данных:
- public обозначается символом ‘+’
- protected обозначается символом ‘#’
- private обозначается символом ‘-‘
На приведённой диаграмме указано, что класс Shape имеет поле данных position с квалификатором доступа private; методы Draw, Erase, MoveTo. При этом указано, что метод Draw имеет входной параметр dc.
Диаграмма классов отражает отношения между классами.
На диаграмме указано, что классы Box, Circle и Line наследуют классу Shape. При этом дополнительно указано, что класс Box содержит дополнительный атрибут side, хранящий длину стороны квадрата, а класс Circle содержит атрибут, хранящий радиус окружности.
Класс View рисует фигуры, используя интерфейса класса Shape.
На диаграмме может быть отражена компоновка объектов посредством агрегирования и композиции. Они отражают отношение целое/часть.
На данной диаграмме указано, что класс Drawing (чертёж) состоит из фигур. При этом он не владеет ими (ромб на конце соединения не закрашен). Фигуры временно находятся на рисунке. То есть они не являются неотъемлемой частью рисунка. Такая связь в UML называется агрегированием.
Цифра «1» и символ «*» отражают «кратность» связи. На диаграмме указано, что фигура может содержаться только на одном чертеже, при этом на чертеже может содержаться неограниченное число фигур.
На диаграмме показано, что класс Drawing состоит из заголовка (Header), подписи (Footer), слоёв (Layer), сетки (Grid) и истории изменений (History). При этом указано, что заголовок и подпись могут быть только в одном экземпляре, число слоёв не ограничено. Сетка и история команд также могут быть в одном экземпляре. Для отображения факта того, что Drawing состоит из этих объектов используется отношение композиции.
Сетка может отображаться или скрываться, для чего в ней содержится атрибут is_on.
История команд агрегирует команды в произвольном количестве.
Диаграмма последовательности (Sequence diagram)
Диаграмма последовательности является одной из диаграмм взаимодействий и отражает последовательность выполнения программы в терминах взаимодействия объектов.
Диаграммы последовательностей читаются сверху вниз. Вверху диаграммы указывается класс или объект. При этом имя класса отделяется от имени объекта двоеточием. Если указывается имя класса, оно указывается с префиксом “:’. Если указывается имя объекта и имя класса, то имя объекта указывается первым, а с именем класса его разделяет символ “:”. Для того, чтобы отличать имена классов и объектов, имена объектов подчёркиваются.
Вертикальные пунктирные линии представляют жизненный путь объектов (время жизни), а вертикальные прямоугольники – время выполнения рассматриваемого метода.
Горизонтальные стрелки показывают передачу управления (посылка сообщения, вызов метода).
На диаграмме показано, что функция main посылает сообщение Draw (вызывает соответствующий метод) объекту класса Drawing. Он в свою очередь последовательно вызывает рисование сетки и объектов.
Для выполнения дисковых чтения или записи (Serialize - передача в последовательный поток) main посылает сообщение Serialize объекту класса Drawing, который в свою очередь вызывает посылает аналогичное сообщение объектам.
Диаграммы состояний (State machine diagram)
Диаграммы состояний отражают переходы системы между различными состояниями. На диаграмме указываются: точки входа и выхода (начальное и конечное состояние), промежуточные состояния и переходы между состояниями.
Каждое состояние или переход могут быть снабжены дополнительной информацией.
На диаграмме показана реализация механизма перетаскивания объекта в редакторе. Внешние события инициируют переходы. Наведение курсора на объект приводит к подсвечиванию объекта. Нажатие левой клавиши мыши – к захвату объекта. При входе в состояние «Объект захвачен» производится сохранение смещения курсора относительно объекта. Далее, когда перемещается курсор, перемещается сам объект. Отпускание левой клавиши мыши приводит к завершению захвата объекта. При этом обновляется его состояние в редакторе.
В правом нижнем углу показан пример записи комментария в нотации UML.
Другие виды диаграмм
Кроме рассмотренных диаграмм существуют следующие диаграммы:
- Компонентов
- Кооперации
- Развёртывания
- Объектов
- Пакетов
- Деятельности
- Обзора взаимодействия
- Синхронизации
Подробное рассмотрение этих диаграмм выходит за рамки лекционного курса. Рекомендую ознакомиться с этими видами диаграмм по мере возникновения практических потребностей.
Об использовании UML
Язык UML является средством визуального документирования архитектуры программной системы. Он служит для обеспечения коммуникации между заинтересованными сторонами при обсуждении проекта, для более простого представления системы при её изучении.
Человеческое восприятие устроено таким образом, что человеку проще воспринимать визуальные образы, чем текст. Поэтому при рассмотрении сложной системы визуальное представление позволяет легче пояснить или понять объясняемую подсистему.
Главное при использовании UML понимать, что это средство пояснения. Не имеет смысла рисовать диаграмму всей системы в целом в предельной детализации. В этом никто и никогда не разберётся. Очень редки случаи, когда имеет смысл подобная полная диаграмма. Реальный смысл использования диаграмм – визуальное пояснение конкретного инженерного решения, использованного в программной системе.
С точки зрения человеческого восприятия наиболее эффективно, если объектов на диаграмме будет не более семи. В этом случае диаграмма воспринимается как «целое» и нет необходимости делить её при изучении на части и понимать каждую часть отдельно.
При этом небольшим числом объектов может быть описана как вся система, так и какой-то локальный модуль. Вы лишь выбираете масштаб показываемого участка и рассматриваете систему на том уровне, на котором хотите дать необходимые пояснения.
При использовании диаграмм появляется возможность эффективного использования абстрагирования. Показывайте только те элементы, которые существенны для данной конкретной диаграммы. Например, на диаграмме классов не надо выписывать все атрибуты и операции каждого класса. Показывайте только те, которые имеют отношение к тому, о чём рассказывается на диаграмме. Это очень существенное преимущество перед исходным кодом, в котором со временем образуется большое число элементов, относящихся к разным задачам. На диаграмме у вас есть возможность выделить только существенное для рассматриваемого вопроса.
Различные виды диаграмм являются взглядами на одну и ту же систему с различных сторон – структуры, динамики взаимодействий, состояний, интерфейсов, физического развёртывания. Ещё раз повторюсь, что нет смысла рисовать все виды диаграмм для всей системы. Используйте диаграммы лишь для того, чтобы показать конкретную часть системы, когда это требуется в ходе обсуждения или описания системы.
Каждая диаграмма должна обязательно отвечать на вопрос «что именно она поясняет». Если ответ «Это схема всей системы» или «Это все классы этого модуля» - диаграмма, скорее всего, является неверной. Правильные ответы: «Это диаграмма взаимодействия с пользователем», «Это схема решения для отмены команд», «Это диаграмма состояний системы управления лифтом».