Как создать уникальный индекс для полей с возможными значениями null (Oracle 11g)?
вот пример таблицы с 3 столбцами (ID, UNIQUE_VALUE, UNIQUE_GROUP_ID)
Я хочу ниже записи могут быть разрешены:
(1, NULL, NULL)
(2, NULL, NULL)
или
(3, NULL, 7)
(4, 123, 7)
или (Примечание: это условие не допускаются в unique index
, ни unique constraint
)
(5, NULL, 7)
(6, NULL, 7)
и это не может быть разрешено:
(7, 123, 7)
(8, 123, 7)
Я создал уникальный индекс для последних 2 столбцов, но только первые 2 примера могут быть разрешены.
можно ли позволить db проверяем уникальность этих 2 столбцов только тогда, когда оба не равны нулю?
2 ответов
вы хотите только обеспечить уникальность строк, где оба UNIQUE_VALUE
и UNIQUE_GROUP_ID
не являются null. Для этого можно использовать уникальный функциональный индекс:
CREATE UNIQUE INDEX func_based_index ON the_table
(CASE WHEN unique_value IS NOT NULL
AND unique_group_id IS NOT NULL
THEN UNIQUE_VALUE || ',' || UNIQUE_GROUP_ID
END);
вы можете использовать функцию nvl, чтобы избежать нулей и вместо этого поместить другое значение,
create unique index func_idx on TEST_TABLE (nvl(UNIQUE_VALUE,1), UNIQUE_GROUP_ID);
недостатком является то, что ваш индекс будет больше, и если вы хотите искать значения null, вам придется использовать функцию nvl, чтобы избежать table_access_full.
также все значения null будут расположены под одной ветвью индекса, поэтому убедитесь, что ваши гистограммы обновлены.
надеюсь, это вам поможет:)