UML2 и унифицированный процесс. Джим арлоуайла нейштадтпрактический объектно ориентированныйанализ и проектированиеu
Скачать 6.08 Mb.
|
Рис. 12.5. Примеры пиктограмм линии жизни 12.7. Сообщения 271 12.7. Сообщения Сообщение – это особый вид коммуникации между линиями жизни. Сообщение представляет особый тип коммуникации между двумя ли ниями жизни. Такое взаимодействие может включать: • вызов операции – сообщение вызова; • создание или уничтожение экземпляра – сообщение создания или уничтожения; • отправку сигнала. Cообщение вызова, получаемое линией жизни, является запросом на вызов операции, имеющей аналогичную сообщению сигнатуру. Таким образом, для каждого поступающего на линию жизни сообщения вы зова в классификаторе этой линии жизни должна существовать соот ветствующая операция. UML допускает несовпадение (рассинхрониза цию) сообщений и операций на диаграммах взаимодействий, что обес печивает возможность динамической и гибкой работы с моделью. Од нако в ходе дальнейшего анализа сообщения и операции должны быть синхронизированы. Когда линия жизни посылает сообщение, в ней находится фокус управ ления (focus of control), или активация (activation). По мере развития взаимодействия во времени активация перемещается между линиями жизни. Это движение называют потоком управления (flow of control). Сообщения отображаются в виде стрелок между линиями жизни. Если линия жизни имеет пунктирный «хвост» (как на диаграммах последо вательностей), сообщения обычно размещают между пунктирными линиями. В противном случае сообщения выстраиваются между пик тограммами линий жизни. В данной книге приводится множество примеров изображения сообщений. Существует семь типов сообщений (табл. 12.2). Таблица 12.2 Синтаксис Имя Семантика Синхронное сообщение Отправитель ожидает завершения выпол нения сообщения получателем. Асинхронное сообщение Отправитель посылает сообщение и продол жает исполнение – он не ожидает возврата от получателя. Возврат Получатель сообщения возвращает фокус управления отправителю этого сообщения. Создание объекта Отправитель создает экземпляр классифи катора, определенного получателем. aMessage(aParameter) aMessage(aParameter) : A «create» aMessage() 272 Глава 12. Реализация прецедентов Таблица 12.2 (продолжение) 12.7.1. Синхронные, асинхронные и сообщения возврата При синхронном вызове сообщения отправитель ожидает завершения выполнения получателем запрашиваемой операции. При асинхрон ном отправитель ничего не ожидает, а переходит к следующему этапу. Для аналитических моделей различие между синхронными и асин хронными сообщениями обычно является слишком высоким уровнем детализации. При анализе нас не интересует глубокая семантика про цесса обмена сообщениями. Достаточно того факта, что сообщение от правлено. В этом случае все сообщения можно показывать как синхрон ные или асинхронные – это на самом деле не важно. Мы предпочитаем все сообщения отображать как синхронные, потому что это наиболее не свободный вариант. Синхронные сообщения показывают прямую по следовательность вызовов операций, тогда как асинхронные сообщения указывают на возможный параллелизм. При проектировании различие между синхронными и асинхронными сообщениями может иметь значение для создания параллельных пото ков управления. На уровне анализа реализаций прецедентов сообщение возврата мож но показывать или не показывать – по желанию разработчика. Обыч но они не имеют особого значения, и их наносят на диаграмму, только если это не загромождает ее. 12.7.2. Сообщения создания и уничтожения В OO анализе обычно нас не интересует конкретная семантика созда ния или уничтожения объекта, но понимать, что происходит, необхо димо. Поэтому уделим внимание этому вопросу. Синтаксис Имя Семантика Уничтоже ние объекта Отправитель уничтожает получателя. Если у линии жизни есть «хвост», он за вершается символом X. Найденное сообщение Отправитель сообщения находится вне об ласти видимости взаимодействия. Используется, когда необходимо показать получение сообщения без указания его ис точника. Потерянное сообщение Сообщение никогда не достигает точки своего назначения. Может использоваться для обозначения состояний ошибки, при которых пропада ют сообщения. «destroy» 12.7. Сообщения 273 Сообщение создания объекта обычно изображается как сплошная ли ния с открытой стрелкой. Создание объекта можно показать с помо щью сообщения со стереотипом «create» (создать). Или можно послать конкретное именованное сообщение создания объекта, которое также может быть обозначено стереотипом «create». В C++, C# или Java опе рации создания объектов являются специальными операциями, кото рые называют конструкторами. Имя конструктора совпадает с именем класса. Конструкторы не имеют возвращаемого значения, они могут иметь от нуля и более параметров. Например, для создания нового объекта Account можно было бы послать сообщение Account() и инициа лизировать его атрибут accountNumber некоторым значением. Однако конструкторы есть не во всех языках программирования. Например, в Smalltalk было бы послано сообщение «create» init: accountNumber. Сообщение уничтожения объекта показывают сплошной линией с от крытой стрелкой и стереотипом «destroy» (уничтожить). Уничтожение означает, что экземпляр классификатора, на который ссылается целе вая линия жизни, больше не доступен для использования. Если у ли нии жизни есть «хвост», он должен завершаться большим крестом в точке уничтожения. Для уничтожения объектов нет возвращаемого значения. В разных языках программирования семантика уничтожения различ на. Например, в С++ уничтожение обычно явно обрабатывается про граммистом, и при уничтожении объекта гарантированно иницииру ется специальный метод (если он существует), называемый деструкто ром. Этот метод часто используется для проведения операций очистки, таких как высвобождение ресурсов, например файлов или соединений с базой данных. Вызов деструктора высвобождает память, выделен ную под объект. В таких языках программирования, как Java и C#, уничтожение объ ектов обрабатывается виртуальной машиной с помощью механизма под названием «сборка мусора». Например, если на объект Java программы больше не ссылается ни один другой объект, он помечается как готовый к уничтожению. Уничтожение произойдет в некоторый момент време ни в соответствии с алгоритмом сборки мусора, но вы не знаете, когда это случится! У объектов в Java и C# могут быть методы «финализато ры», которые будут исполняться в момент реального уничтожения, осу ществляемого сборщиком мусора. Однако использовать этот метод опас но, потому что мы точно не знаем, когда сборщик мусора вызовет его. 12.7.3. Найденные и потерянные сообщения Обычно в анализе найденные и потерянные сообщения могут быть проигнорированы. Мы рассматриваем их здесь в основном для полно ты обсуждения. Найденные сообщения могут быть полезны, если необходимо показать получение сообщения классом, но неизвестно (в данный момент време 274 Глава 12. Реализация прецедентов ни), откуда поступило это сообщение. На практике такое встречается редко. Потерянные сообщения позволяют показать, что сообщение потеряно – оно никогда не достигает точки своего назначения. Это может быть по лезно при проектировании, чтобы показать, как могут теряться сооб щения в условиях возникновения ошибки. Однако у нас никогда не возникало крайней необходимости использовать это понятие. 12.8. Диаграммы взаимодействий Диаграммы взаимодействий UML могут использоваться для модели рования любого типа взаимодействия между экземплярами классифи каторов. В частности, в реализации прецедентов диаграммы взаимо действий используются для моделирования взаимодействий между объектами, реализующими прецедент или его часть. Существует четы ре разных типа диаграмм взаимодействий, каждый из которых делает акцент на различных аспектах взаимодействия. Четыре типа диаграмм взаимодействий предоставляют разные проек ции взаимодействий объектов. • Диаграммы последовательностей (sequence diagrams) акцентируют внимание на временной упорядоченности сообщений. Обычно поль зователи лучше понимают диаграммы последовательностей, чем коммуникационные диаграммы, поскольку они намного легче чи таются. Как правило, коммуникационные диаграммы очень быстро загромождаются. Диаграммы последовательностей обсуждаются в разделе 12.9. • Коммуникационные диаграммы (communication diagrams) выделя ют структурные отношения между объектами и очень полезны при анализе, особенно для создания эскиза совместной работы объек тов. В UML 2 эти диаграммы предлагают только лишь подмножест во функциональности диаграмм последовательностей. Коммуника ционные диаграммы обсуждаются в разделе 12.11. • Диаграммы обзора взаимодействий (interaction overview diagrams) показывают, как сложное взаимодействие реализуется рядом прос тых взаимодействий. Это особый случай диаграммы деятельности, в которой узлы ссылаются на другие взаимодействия. Они полезны для моделирования потока управления системы. Диаграммы обзо ра взаимодействий обсуждаются в разделе 15.12. • Временные диаграммы (timing diagrams) обращают внимание на фактическое время взаимодействия. Их основное назначение – по мочь оценить временные затраты. Временные диаграммы рассмат риваются в разделе 20.7. 12.9. Диаграммы последовательностей 275 Диаграммы последовательностей и коммуникационные диаграммы являются самыми важными с точки зрения реализации прецедентов. Оставшаяся часть этой главы посвящена их детальному обсуждению. 12.9. Диаграммы последовательностей Диаграммы последовательностей представляют взаимодействия меж ду линиями жизни как упорядоченную последовательность событий. Это самая богатая и гибкая форма диаграммы взаимодействий. Диаграммы последовательностей представляют взаимодействия между линиями жизни как упорядоченную последовательность событий. Иногда моделирование начинают с создания эскиза реализации преце дента с помощью коммуникационной диаграммы (раздел 12.11), пото му что на диаграмме легко размещать и соединять линии жизни. Од нако если необходимо сфокусировать внимание на установлении фак тической последовательности событий, удобнее работать с диаграм мой последовательностей. 12.9.1. Линии жизни и сообщения Чтобы разобраться с линиями жизни и сообщениями, возьмем пример из простой системы регистрации курсов. Рассмотрим реализацию пре цедента AddCourse (добавить курс) (рис. 12.6). Чтобы пример был прос тым, сохранен очень высокий уровень абстракции этого прецедента. Прецедент: AddCourse Главные актеры: Registrar Предусловия: 1. Registrar вошел в систему. Постусловия: 1. Новый курс добавлен в систему. Основной поток: 1. Registrar выбирает «add course». 2. Registrar вводит имя нового курса. 3. Система создает новый курс. Альтернативные потоки: CourseAlreadyExists ID: 8 Краткое описание: Добавляет детали нового курса в систему. Второстепенные актеры: Нет. Рис. 12.6. Спецификация прецедента AddCourse 276 Глава 12. Реализация прецедентов Исходный анализ созданного прецедента представлен на рис. 12.7 в ви де высокоуровневой диаграммы классов анализа. Спецификация пре цедента и диаграмма классов обеспечивают объем информации, доста точный для создания диаграммы последовательностей. На рис. 12.8 показана диаграмма последовательностей, реализующая поведение, описанное прецедентом AddCourse. Согласно спецификации UML 2, имена диаграмм взаимодействий могут начинаться с пристав ки sd, для обозначения того, что данная диаграмма является диаграм мой взаимодействий. Довольно странно: sd используется для всех ти пов диаграмм взаимодействий, а не только для диаграмм последова тельностей (sd – sequence diagram)! На данном этапе следует напомнить, что при создании диаграмм после довательностей как части реализации прецедента может обнаружить ся необходимость доработки диаграммы классов анализа или даже прецедента. Это нормально, т. к. все это – часть процесса анализа. RegistrationManager Course 1 0..* courses Student 1 0..* students registration 0..* 0..* Рис. 12.7. Диаграмма классов анализа прецедента AddCourse :Registrar :RegistrationManager uml:Course addCourse( "UML" ) «create» из примечаний может быть образован «сценарий», описывающий поток линия жизни sd AddCourse сообщение создания объекта синхронное сообщение объект создается в данной точке сообщения возврата активация The Registrar selects "add course". The system creates the new Course. Рис. 12.8. Диаграмма последовательностей прецедента AddCourse 12.9. Диаграммы последовательностей 277 Прецедент, диаграмма классов анализа и диаграмма последовательно стей – все они вместе эволюционируют со временем. Рассмотрим диаграмму последовательностей, приведенную на рис. 12.8. Время на диаграммах последовательностей развивается сверху вниз, линии жизни выполняются слева направо. Линии жизни размещают ся горизонтально, чтобы минимизировать число пересекающихся ли ний на диаграмме. Их местоположение относительно вертикальной оси отражает момент их создания. Пунктирная линия, находящаяся внизу, показывает существование линии жизни в течение времени. Диаграммы взаимодействий не являются дословными копиями преце дента; это иллюстрации того, как классы анализа реализуют поведение прецедента. Обратите внимание, что рис. 12.8 показывает реализацию поведения прецедента, но не является точным представлением каждого его шага. Это важный момент. В шагах 1 и 2 участвует какой то пользователь ский интерфейс, которым не занимаются всерьез вплоть до этапа проек тирования, поэтому на диаграмме последовательностей он опущен. Слой пользовательского интерфейса, который помогает прояснить не которые вещи, может быть добавлен в диаграмму последовательностей во время проектирования (раздел 20.4). В анализе нас интересует толь ко основное поведение классов анализа. Давайте рассмотрим другой пример – прецедент DeleteCourse (удалить курс) из системы регистрации курсов (рис. 12.9). В данном случае происходит уничтожение объекта. Уничтожение объ екта обозначается большим крестом, завершающим линию жизни, как Прецедент: DeleteCourse Главные актеры: Registrar Предусловия: 1. Registrar вошел в систему. Постусловия: 1. Курс удален из системы. Основной поток: 1. Registrar выбирает «delete cource». 2. Registrar вводит имя курса. 3. Система удаляет курс. Альтернативные потоки: CourseDoesNotExist ID: 8 Краткое описание: Удаляет курс из системы. Второстепенные актеры: Нет. Рис. 12.9. Спецификация прецедента DeleteCourse 278 Глава 12. Реализация прецедентов показано на рис. 12.10. Если момент уничтожения объекта неизвестен или неважен, линия жизни завершается без креста. На рис. 12.10 также представлено самоделегирование: линия жизни объекта посылает сообщение самой себе. Это создает вложенную акти вацию (см. следующий раздел). Самоделегирование распространено в ОО системах. Объекты предлагают ряд открытых сервисов (откры тых операций), которые могут быть вызваны клиентскими объектами. Но, как правило, они также имеют и закрытые «вспомогательные» опе рации, разработанные специально для вызова самим объектом. В дан ном примере линия жизни :RegistrationManager посылает сама себе сооб щение findCourse( "UML" ), чтобы найти UML объект курса, если таковой существует. Закрытые операции объекта могут быть вызваны только самим объектом средствами самоделегирования. 12.9.2. Активации Вытянутые прямоугольники, расположенные на пунктирной линии под линией жизни, показывают, когда на данной линии жизни нахо дится фокус управления. Эти прямоугольники называются активаци ями, или фокусом управления. Активации показывают, когда фокус управления располагается в дан ной линии жизни. Отметим, что в книге «The Unified Modeling Language Reference Manu al, Second Edition» [Rumbaugh 1] активация определяется как «термин UML 1, замененный на термин “описание выполнения”». Однако нигде в «Unified Modeling Language: Superstructure, version 2.0» [UML2S] :Registrar :RegistrationManager uml:Course deleteCourse( "UML" ) sd DeleteCourse объект уничтожается в этот момент «destroy» самоделегирование findCourse( "UML" ) вложенная активация Рис. 12.10. Самоделегирование 12.9. Диаграммы последовательностей 279 термина «описание выполнения» («execution specification») нам найти не удалось, тогда как там есть и «активация», и «фокус управления». Отсюда можно сделать единственный вывод о том, что «активация» и «фокус управления» являются стандартными терминами. Мы вспом нили об этом, потому что в литературе может встретиться термин «опи сание выполнения» как синоним активации, поскольку он включен в книгу [Rumbaugh 1]. На рис. 12.8 фокус управления сначала находится на актере :Registrar. Он посылает сообщение addCourse( "UML" ) актеру :RegistrationManager, ко торый инициирует операцию addCourse(…) с параметром "UML". Во вре мя выполнения этой операции фокус управления находится у :Registra tionManager. Однако обратите внимание, что этот фокус управления вло жен в фокус управления актера :Registrar. Это вполне нормально – один объект, имеющий фокус управления, инициирует операцию другого объекта, создавая вложенный фокус управления. Затем этот объект может инициировать операцию еще одного объекта, еще более углуб ляя вложенность фокуса управления, и т. д. В рамках выполнения операции addCourse(…) актер :RegistrationManager создает новый объект uml:Course. В последние годы активации вышли из моды. Многие разработчики моделей не утруждают себя их отображением. Отчасти это объясняется плохой поддержкой активаций некоторыми инструментами UML, от части тем, что обычно активации не так важны, особенно в аналитиче ских моделях. В исполняющейся ОО системе активации и так просмат риваются через обычную семантику вызова операции. На практике чи тать сложные диаграммы последовательностей без активаций может быть немного проще. Мы используем активации, только если они не уменьшают читаемость диаграммы. |