Подзапрос в ограничении кортежа DB2 - PullRequest
0 голосов
/ 08 сентября 2010

В моем курсе по базе данных мы используем книгу (Система баз данных - Полная книга), в которой говорится, что следующее является допустимым оператором создания таблицы в стандартном SQL:

CREATE TABLE Participants (
    meetid INT NOT NULL,
    -- ...
    CONSTRAINT RoomConstraint
        CHECK (1 >= ALL (SELECT num FROM Numbers)
);

Но DB2 жалуется и дает 20 возможных объяснений, почему этот оператор не выполняется.

Итак, DB2 не поддерживает подзапросы в кортежных ограничениях? А если нет, то является ли TRIGGER единственным решением для принудительного применения ограничения подзапроса?

Обновление: Я нашел эту ссылку, которая утверждает, что это невозможно: http://bytes.com/topic/db2/answers/837390-can-constraint-replace-trigger

Но опять же, ТРИГГЕР - единственный выход? (Я пытаюсь установить связь, при которой атрибут может ссылаться на две разные таблицы (это не моя база данных))

Обновление 2: Без ALL также не работает:

CREATE TABLE Foo (
   meetid INT NOT NULL,
   CHECK (meetid IN (SELECT meetid FROM Foo)));

Обновление 3: Идея состоит в том, что мне нужен внешний ключ, который ссылается на две таблицы, подобные следующей:

Table Participants (pid, ...)
Table Rooms (room, ...)
Table People (userid, ...)

По сути, pid должен существовать либо в Комнаты (комната атрибутов), либо в Люди (идентификатор пользователя атрибута). Я мог бы частично решить эту проблему с помощью ограничения строк, которое проверяет, находится ли pid в Rooms или People, но DB2 не позволит мне. (Я знаю, что есть много других вещей, которые нужно ограничить для эмуляции внешнего ключа)

Ответы [ 2 ]

1 голос
/ 08 декабря 2010

Как реализовать необязательное (или альтернативное) ограничение проверки внешнего ключа в SQL Server

create function dbo.meetidinmeetings(@meetid)
returns bit
as
begin
declare @return bit
as
if exists(select 1 from meetings where meetid = @meetid)
set @return =1 
else
set @return = 0
return @return
end

тогда ...

CREATE TABLE Foo (
meetid INT NOT NULL,
ismeeting bit NOT NULL DEFAULT 0

ALTER TABLE FOO
ADD CONSTRAINT CHK_FOO_MEETID
CHECK ((ismeeting = 0) or (ismeeting = 1 and dbo.is_meetidinmeetings(meetid) = 1)))
0 голосов
/ 08 сентября 2010

ALL () - это не стандартный SQL ** - это расширение T-SQL.DB2 не поддерживает это.

Я не уверен, что вы пытаетесь сделать со своим ограничением - похоже, вы пытаетесь убедиться, что каждое значение num в таблице Numbers меньше илиравно 1. Если это действительно так, вы должны добавить ограничение на таблицу Numbers, а не на Участники.

** стандарт SQL92, и я не верю, что он был добавлен в SQL99 или SQL2003

...