Студопедия
Случайная страница | ТОМ-1 | ТОМ-2 | ТОМ-3
АвтомобилиАстрономияБиологияГеографияДом и садДругие языкиДругоеИнформатика
ИсторияКультураЛитератураЛогикаМатематикаМедицинаМеталлургияМеханика
ОбразованиеОхрана трудаПедагогикаПолитикаПравоПсихологияРелигияРиторика
СоциологияСпортСтроительствоТехнологияТуризмФизикаФилософияФинансы
ХимияЧерчениеЭкологияЭкономикаЭлектроника

Неуникальные (или почти уникальные) ключи

Читайте также:
  1. II. Исключить «лишнее» понятие
  2. V. Заключительные положения
  3. VII. Заключительные положения
  4. Билет № 30 Надзор прокурора на заключительном этапе расследования. Соотношение прокурорского надзора и судебного контроля.
  5. В горячей воде почти в три раза повышается растворимость
  6. В исключительных случаях руководителем может быть поручено работнику выполнение работ, не предусмотренных настоящей должностной инструкцией.
  7. Весть о прорыве блокады на кораблях и частях флотилии была встречена с исключительной радостью. Состоялись митинги, на которых личный состав брал новые боевые обязательства.

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

"Столько говорили о важности уникальных ключей для нормализации информационной модели и в конце концов опять пришли к неуникальным ключам?" — скажете вы. Да, ключ может быть уникальным в концептуальной модели, но при преобразовании ее в логическую модель, которую мы хотим реализовать в виде таблиц Oracle, он теряет свою уникальность. Например, если в ключ была включена метка даты и времени, то возможны проблемы. Время в Oracle7 округляется до секунд, поэтому, если мы создадим за одну секунду две строки с идентичными ключами, никакая метка времени нам не поможет.

Рассмотрим пример, приведенный на рис. 6.1. Предположим, что мы можем создать несколько версий исходного кода с одним и тем же именем каталога и файла. Сделать каждую версию уникальной можно было бы путем ввода в ключ столбца INSERTDATETIME ("Вставить дату и время"), поскольку вручную создать две версии одного и того же исходного кода за одну секунду весьма сложно. Но если мы используем генератор кода, который очень быстро создает один за другим два варианта, то возможны проблемы. В таких случаях мы будем получать сообщения об ошибках периода выполнения о нарушении ограничения UNIQUE. Чтобы исправить ситуацию, можно изъять метку даты и времени из ключа и ввести в него простой Целочисленный номер версии, как показано на рис. 6.2.


Рис. 6.1. Таблица с первичным ключом, который "почти" уникален


Рис. 6.2. Таблица с первичным ключом, который полностью уникален

Теперь, даже если значения системных даты и времени по какой-то причине сдвинутся назад (например, при переходе на зимнее время), столбец VERSION# сообщит нам истинную последовательность версий. Учтите, что дефекты такого рода (когда записи могут "расположиться" в неправильном порядке) очень легко предотвратить, но довольно сложно исправить после сдачи системы в эксплуатацию.

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

SELECT MAX(version#) + 1
FROM source_code
WHERE directory =:id
AND filename =:f;

Операция чтения осуществляется здесь без блокировки, поэтому один и тот же ответ могут получить несколько пользователей. Даже если вы уже выполнили операцию SELECT FOR UPDATE над файлом, который вы считаете последней версией, это не помешает другому пользователю выдать запрос SELECT MAX()... и получить такой же номер версии. В результате два пользователя одновременно могут пытаться создать одну и ту же версию, и один из них потерпит неудачу из-за нарушения ограничения UNIQUE.

Возможна также ситуация, в которой нескольким модулям нужно извлечь последнюю (только последнюю) версию конкретного файла. Чтобы найти ее, придется воспользоваться приблизительно таким запросом:

SELECT...
FROM source_code
WHERE directory =:id
AND filename =:f
AND version# = (SELECT MAX(s2.version#)
FROM source_code s2
WHERE s2.directory =:id
AND s2.filename =:f);

Давайте проанализируем этот запрос. Он не очень эффективен, хотя в последних версиях скорость его выполнения и увеличилась. Это является следствием того, что в нем производится два поиска в индексе по первичному ключу. Если вы читали предыдущую главу, то наверняка поймете, что, во-первых, таблицу SOURCE_CODE следует назвать SOURCE_CODE_VERSIONS (ВЕРСИИ_ИСХОДНОГО_КОДА) и, во-вторых, следует ввести новую таблицу SOURCE_CODE для хранения всех атрибутов файла, приемлемых для каждой версии. Теперь мы можем ввести в эту главную таблицу производный столбец для регистрации номера последней версии исходного кода.


Дата добавления: 2015-08-09; просмотров: 102 | Нарушение авторских прав


Читайте в этой же книге: Как работает индекс? | Примечание | Отключение индексов | Составные индексы | Примечание | Свойства хеш-ключей | Пример хеш-кластера | Индексные кластеры |
<== предыдущая страница | следующая страница ==>
Исследование синтетических, или суррогатных, ключей| Замена длинных каскадных ключей суррогатными

mybiblioteka.su - 2015-2024 год. (0.011 сек.)