Идентифицирующие и неидентифицирующие связи
В IDEF1X концепция зависимых и независимых сущностей усиливается типом взаимосвязей между двумя сущностями. Если вы хотите, чтобы внешний ключ передавался в дочернюю сущность (и, в результате, создавал зависимую сущность), то можете создать идентифицирующую связь между родительской и дочерней сущностями.
Идентифицирующие взаимосвязи обозначаются сплошной линией между сущностями.
Неидентифицирующие связи, являющиеся уникальными для IDEF1X, также связывают родительскую сущность с дочерней
Неидентифицирующие связи используются для отображения другого типа передачи атрибутов внешних ключей – передача в область данных дочерней сущности (под линией).
Так как переданные ключи в неидентифицирующей связи не являются составной частью первичного ключа дочерней сущности, то этот вид связи не проявляется ни в одной идентифицирующей зависимости. В этом случае и ОТДЕЛ, и СОТРУДНИК рассматриваются как независимые сущности.
Тем не менее, взаимосвязь может отражать зависимость существования, если бизнес правило для взаимосвязи определяет то, что внешний ключ не может принимать значение NULL. Если внешний ключ должен существовать, то это означает, что запись в дочерней сущности может существовать только при наличии ассоциированной с ним родительской записи.
Роль
Имя роли (функциональное имя) – это синоним атрибута внешнего ключа, который показывает, какую роль играет атрибут в дочерней сущности.
В примере, приведенном на рис. П8, в сущности «СТРАХОВАНИЕ» внешний ключ «Код клиента» имеет функциональное имя «Кто страхуется», которое показывает, какую роль играет этот атрибут в сущности. По умолчанию в списке атрибутов показывается только имя роли. Для отображения полного имени атрибута (как функционального имени, так и имени роли) следует в контекстном меню, которое появляется, если щелкнуть правой кнопкой мыши по любому месту диаграммы, не занятому объектами модели, выбрать пункт Entitiy Display и затем включить опцию Rolename/Attribute. Полное имя показывается как функциональное имя и базовое имя, разделенные точкой (смотри рис. П8).
Обязательным является применение имен ролей в том случае, когда два или более атрибута одной сущности определены по одной и той же области, т. е. они имеют одинаковую область значений, но разный смысл.
Рис. П8. Имена ролей внешних ключей
На рис. П9 сущность АЭРОПОРТ содержит данные обо всех аэропортах, между которыми организованы рейсы самолетов. Информация о полете, которая содержится в сущности ПОЛЕТ, включает пункт назначения и пункт отправления самолетов. Следовательно, сущности ПОЛЕТ и АЭРОПОРТ должны быть связаны дважды и первичный ключ – Код аэропорта должен дважды мигрировать в сущность ПОЛЕТ в качестве внешнего ключа. Необходимо различать эти атрибуты, которые содержат информацию об аэропорте, из которого вылетает самолет, и аэропорте, в который прилетает самолет. Они имеют разный смысл, но ссылаются на одну и ту же сущность АЭРОПОРТ (имеют общую область значений). В примере на рис. П9 атрибуты получили имена ролей «Пункт оправления» и «Пункт назначения».
Другим примером обязательности присвоения имен ролей являются рекурсивные связи (иногда их называют «рыболовным крючком» – fish hook), когда одна и та же сущность является и родительской и дочерней одновременно.
Рис. П9. Случай обязательности имен ролей
При задании рекурсивной связи атрибут должен мигрировать в качестве внешнего ключа в состав неключевых атрибутов той же сущности. Атрибут не может появиться дважды в одной сущности под одним именем, поэтому обязательно должен получить имя роли. На рис. П10 сущность Сотрудник содержит атрибут первичного ключа Код сотрудника. Информация о руководителе сотрудника содержится в той же сущности, поскольку руководитель работает в той же организации. Чтобы сослаться на руководителя сотрудника, следует создать рекурсивную связь (на рис. 9 связь руководит) и присвоить имя роли (Руководитель). Заметим, что рекурсивная связь может быть только неидентифицирующей. В противном случае внешний ключ должен был бы войти в состав первичного ключа и получить при генерации схемы признак NOT NULL. Это сделало бы невозможным построение иерархии, – у дерева подчиненности должен быть корень, – сотрудник, который никому не подчиняется в рамках данной организации.
Связь «руководит/подчиняется» на рис. П10 позволяет хранить древовидную иерархию подчиненности сотрудников. Такой вид рекурсивной связи называется иерархической рекурсией (hierarchical recursion) и задает связь, когда руководитель (экземпляр родительской сущности) может иметь множество подчиненных (экземпляров дочерней сущности), но подчиненный имеет только одного руководителя (смотри рис. П10).
Другим видом рекурсии является сетевая рекурсия (network recursion), когда руководитель может иметь множество подчиненных и, наоборот, подчиненный может иметь множество руководителей. Сетевая рекурсия задает паутину отношений между экземплярами родительской и дочерней сущностей. Это случай, когда сущность находится сама с собой в связи «многие ко многим». Для разрешения связи «многие ко многим» необходимо создать новую сущность (подробно связь «многие ко многим» будет рассмотрена ниже).
Рис. П10. Подчиненность экземпляров сущности в иерархической рекурсии
На рис. П3 рассмотрен пример реализации сетевой рекурсии. Структура моделирует отношения субординации между сотрудниками любой сложности. Поскольку отношение субординации связывает всегда двух людей, от сущности Сотрудник к сущности отношения субординации установлены две идентифицирующие связи с именами ролей «Руководитель» и «Подчиненный». Каждый сотрудник может быть в отношениях «руководит/подчиняется» с любым другим сотрудником, но одну и ту же пару сотрудников может связывать один тип отношений субординации.
Связь «многие ко многим»
Так как отношения многие ко многим могут скрыть другие бизнес правила или ограничения, они должны быть полностью исследованы на на уровне ключевой или атрибутивной модели.
Это обусловлено тем, что отношение многие ко многим на ранних стадиях моделирования идентифицируется неправильно, на самом деле представляя два или несколько случаев отношений один-ко-многим между связанными сущностями.
Связь «многие ко многим» может быть преобразована к типу «один ко многим» либо вручную либо автоматически.
Автоматическое преобразование может быть выполнено при переходе на физический уровень. Для автоматического преобразования связи следует во вкладку General диалога Model, Model Property включить опцию Many-To-Many Relationships with Association Table. Преобразование связи включает создание новой таблицы и двух новых связей «один ко многим» от старых к новой таблице. При этом имя новой таблице присваивается автоматически какИмя1_Имя2. Автоматического решения проблемы связи многие-ко-многим не всегда оказывается достаточно.
Для принудительного преобразования связи «многие ко многим» на логическом уровне необходимо щелкнуть по связи правой кнопкой мыши и выбрать пункт меню Create Association Table. Many-To-Many Relationship Transform Wizard. Диалог Many-To-Many Relationship Transform Wizard предлагает 4 шага для преобразования связи. Для перехода к следующему шагу надо щелкнуть по кнопке Next (Далее). На втором и третьем шаге следует задать имя вновь создаваемой таблицы и имя преобразования.
На рис. П11 показан пример связи «многие ко многим». Преподаватель может преподать разные дисциплины, дисциплина может преподаваться разными преподавателями.
Рис. П11. Пример связи «многие ко многим»
В примере таблица Преподават_Предмет имеет смысл учебного занятия, поэтому ее следует переименовать согласно бизнес-логике в «УЧЕБНОЕ ЗАНЯТИЕ». Один и тот же предмет может много раз читаться преподавателем, например в разное время, поэтому для того, чтобы идентифицировать учебное занятие, необходимо в состав первичного ключа сущности «УЧЕБНОЕ ЗАНЯТИЕ» добавить дополнительный атрибут, например дату проведения занятия (рис. П12).
Рис. П12. Сущность УЧЕБНОЕ ЗАНЯТИЕ