Добро пожаловать в форум, Guest  >>   Войти | Регистрация | Поиск | Правила | В избранное | Подписаться
Все форумы / Microsoft SQL Server Новый топик    Ответить
Топик располагается на нескольких страницах: [1] 2 3   вперед  Ctrl      все
 Триггер  [new]
Indi92
Member

Откуда:
Сообщений: 3
Здравствуйте) Помогите написать ограничение(процедуру или триггер), чтобы в таблице "Анкеты" был либо Id_сотрудника, либо Id_соискателя.

К сообщению приложен файл. Размер - 18Kb
27 апр 15, 11:15    [17568138]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
Winnipuh
Member [заблокирован]

Откуда: Київ
Сообщений: 10428
1. покажите ваш вариант, обсудим
2. что значит "либо, либо"?
27 апр 15, 11:17    [17568146]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
iap
Member

Откуда: Москва
Сообщений: 46999
Indi92,

Плохо спроектировано.
Лучше сделать одну таблицу и для сотрудников, и для соискателей с полем "IsSotr".
Для соискателя ссылка на должность - NULL.
Хотя, здесь тоже неточность. Ибо должностей одновременно может быть сколько угодно.
Значит, нужна таблица связок [Сотрудник]-[Должность] с признаком "Основное место работы"
Соответственно, в анкете будет только одна ссылка на объединённую таблицу.
27 апр 15, 11:22    [17568167]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
Winnipuh
Member [заблокирован]

Откуда: Київ
Сообщений: 10428
iap
Indi92,

Плохо спроектировано.
Лучше сделать одну таблицу и для сотрудников, и для соискателей с полем "IsSotr".
Для соискателя ссылка на должность - NULL.
Хотя, здесь тоже неточность. Ибо должностей одновременно может быть сколько угодно.
Значит, нужна таблица связок [Сотрудник]-[Должность] с признаком "Основное место работы"
Соответственно, в анкете будет только одна ссылка на объединённую таблицу.


это уже "разрыв шаблона"
27 апр 15, 11:27    [17568192]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
iap
Member

Откуда: Москва
Сообщений: 46999
Winnipuh
iap
Indi92,

Плохо спроектировано.
Лучше сделать одну таблицу и для сотрудников, и для соискателей с полем "IsSotr".
Для соискателя ссылка на должность - NULL.
Хотя, здесь тоже неточность. Ибо должностей одновременно может быть сколько угодно.
Значит, нужна таблица связок [Сотрудник]-[Должность] с признаком "Основное место работы"
Соответственно, в анкете будет только одна ссылка на объединённую таблицу.


это уже "разрыв шаблона"
Что не так?
27 апр 15, 11:31    [17568222]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
LexusR
Member

Откуда: Novosibirsk
Сообщений: 1873
ISNULL(IdSotr,0) ^ ISNULL(IdSoik,0) = 0
27 апр 15, 11:37    [17568262]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
LexusR
Member

Откуда: Novosibirsk
Сообщений: 1873
сорри

ISNULL(IdSotr,0) ^ ISNULL(IdSoik,0) = 1
27 апр 15, 11:38    [17568270]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
o-o
Guest
LexusR
сорри
ISNULL(IdSotr,0) ^ ISNULL(IdSoik,0) = 1

все ок, только ему еще надо проверять, что там не левое значение вставлено,
а ПК из той или другой таблицы
27 апр 15, 11:41    [17568286]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
Winnipuh
Member [заблокирован]

Откуда: Київ
Сообщений: 10428
iap
Winnipuh
пропущено...


это уже "разрыв шаблона"
Что не так?


да наоборот, всё так, но ТС хотелось бы по-быстрому триггер и сдать работу "преподу"
27 апр 15, 11:48    [17568326]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
LexusR
Member

Откуда: Novosibirsk
Сообщений: 1873
o-o
LexusR
сорри
ISNULL(IdSotr,0) ^ ISNULL(IdSoik,0) = 1

все ок, только ему еще надо проверять, что там не левое значение вставлено,
а ПК из той или другой таблицы

так там судя по картинку foreign key
27 апр 15, 11:50    [17568349]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
Indi92
Member

Откуда:
Сообщений: 3
Winnipuh, вот схема полностью. В отдел кадров приходит новый сотрудник-соискатель и есть работающий сотрудник(у сотрудника и соискателя есть свой ID). Проблема в том, что в Анкете должен быть только один номер: номер соискателя или номер сотрудника.
27 апр 15, 12:04    [17568440]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
Glory
Member

Откуда:
Сообщений: 104760
Indi92
В отдел кадров приходит новый сотрудник-соискатель и есть работающий сотрудник(у сотрудника и соискателя есть свой ID). Проблема в том, что в Анкете должен быть только один номер: номер соискателя или номер сотрудника.

Создание триггера осуществляется командой CREATE TRIGGER, а процедуры - CREATE PROCEDURE
Начните свой скрипт с этих ключевых слов
27 апр 15, 12:06    [17568451]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
Indi92
Member

Откуда:
Сообщений: 3


К сообщению приложен файл. Размер - 70Kb
27 апр 15, 12:07    [17568453]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
o-o
Guest
LexusR
o-o
пропущено...

все ок, только ему еще надо проверять, что там не левое значение вставлено,
а ПК из той или другой таблицы

так там судя по картинку foreign key

да, пардон, там именно что уже есть ФК,
ваше решение просто не катит, т.к. выдаст или то самое неналловое значение (или побитовое ^ обоих), а совсем не 1
т.е. не пропустит правильный ввод, когда всего однозначение not null <> 1
27 апр 15, 12:14    [17568493]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
o-o
Guest
вроде же тогда вообще "в лоб", но понедельник день тяжелый и особо тормозной :)
check((idSotr is null and idSoisk is not null) or (idSotr is not null and idSoisk is null));
27 апр 15, 12:47    [17568675]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
LexusR
Member

Откуда: Novosibirsk
Сообщений: 1873
o-o
LexusR
пропущено...

так там судя по картинку foreign key

да, пардон, там именно что уже есть ФК,
ваше решение просто не катит, т.к. выдаст или то самое неналловое значение (или побитовое ^ обоих), а совсем не 1
т.е. не пропустит правильный ввод, когда всего однозначение not null <> 1

if object_id('dbo._test') is not null drop table dbo._test
create table dbo._test(id int not null identity(1,1) primary key
,IdSotr int
,IdSoik int
)
GO
CREATE TRIGGER CheckData On dbo._test
FOR INSERT, UPDATE
AS 
	SET NOCOUNT ON;
	IF exists(select * from INSERTED
			  where ISNULL(IdSotr,0) ^ ISNULL(IdSoik,0) = 0)
	BEGIN				  
	  RAISERROR('Должна быть только одна ссылка',16,1)	
	  IF @@trancount>0		
		ROLLBACK TRAN
	END  
GO	

insert into dbo._test(IdSotr,IdSoik) values(1,null)
GO
insert into dbo._test(IdSotr,IdSoik) values(null,1)
GO
insert into dbo._test(IdSotr,IdSoik) values(1,1)
GO
insert into dbo._test(IdSotr,IdSoik) values(null,null)
GO

select * from dbo._test
27 апр 15, 12:48    [17568677]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
LexusR
Member

Откуда: Novosibirsk
Сообщений: 1873
o-o
вроде же тогда вообще "в лоб", но понедельник день тяжелый и особо тормозной :)
check((idSotr is null and idSoisk is not null) or (idSotr is not null and idSoisk is null));


Column CHECK constraint for column 'IdSotr' references another column
27 апр 15, 12:51    [17568695]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
o-o
Guest
LexusR
o-o
вроде же тогда вообще "в лоб", но понедельник день тяжелый и особо тормозной :)
check((idSotr is null and idSoisk is not null) or (idSotr is not null and idSoisk is null));


Column CHECK constraint for column 'IdSotr' references another column


чего?
create table dbo.t1 (id int primary key);
insert into dbo.t1 values (1),(2),(3);

create table dbo.t2 (id int primary key);
insert into dbo.t2 values (2),(3),(4);

create table dbo.t (id1 int foreign key references dbo.t1(id),
                    id2 int foreign key references dbo.t2(id));
                    
alter table dbo.t add constraint ck_1 check((id1 is null and id2 is not null) or (id1 is not null and id2 is null));

insert into dbo.t values (1, 3)
--Msg 547, Level 16, State 0, Line 1
--The INSERT statement conflicted with the CHECK constraint "ck_1". The conflict occurred in database "db7", table "dbo.t".
--The statement has been terminated.

insert into dbo.t values (null, 3)
--(1 row(s) affected)
27 апр 15, 12:55    [17568728]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
LexusR
Member

Откуда: Novosibirsk
Сообщений: 1873
o-o
LexusR
пропущено...


Column CHECK constraint for column 'IdSotr' references another column


чего?
create table dbo.t1 (id int primary key);
insert into dbo.t1 values (1),(2),(3);

create table dbo.t2 (id int primary key);
insert into dbo.t2 values (2),(3),(4);

create table dbo.t (id1 int foreign key references dbo.t1(id),
                    id2 int foreign key references dbo.t2(id));
                    
alter table dbo.t add constraint ck_1 check((id1 is null and id2 is not null) or (id1 is not null and id2 is null));

insert into dbo.t values (1, 3)
--Msg 547, Level 16, State 0, Line 1
--The INSERT statement conflicted with the CHECK constraint "ck_1". The conflict occurred in database "db7", table "dbo.t".
--The statement has been terminated.

insert into dbo.t values (null, 3)
--(1 row(s) affected)


я просто в запарке не на таблицу а на оба поля констрайнт пытался кинуть

но мой вариант также работает

alter table dbo.t add constraint ck_1 check(ISNULL(id1,0) ^ ISNULL(id2,0) = 1);
27 апр 15, 13:02    [17568788]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
o-o
Guest
LexusR,

вы не переживайте, кто в запарке, кто в зоопарке (я сегодня сущий жираф, и лучше промолчу про окружающих)
но ваш вариант с "1" не работает, см. объяснение выше
alter table dbo.t drop constraint ck_1;
--Command(s) completed successfully.
 
alter table dbo.t add constraint ck_1 check(ISNULL(id1,0) ^ ISNULL(id2,0) = 1);
---
--Msg 547, Level 16, State 0, Line 1
--The ALTER TABLE statement conflicted with the CHECK constraint "ck_1". The conflict occurred in database "db7", table "dbo.t".

select *
from dbo.t
---
--id1	id2
--NULL	3

select ISNULL(null,0) ^ ISNULL(3,0)
---
--3
27 апр 15, 13:14    [17568854]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
LexusR
Member

Откуда: Novosibirsk
Сообщений: 1873
alter table dbo.t add constraint ck_1 check(isnull(id1,id2)=isnull(id2,id1));
27 апр 15, 13:38    [17569036]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
LexusR
Member

Откуда: Novosibirsk
Сообщений: 1873
LexusR
alter table dbo.t add constraint ck_1 check(isnull(id1,id2)=isnull(id2,id1));

не сработает при одинаковых значениях - всё хватит выделываться - пошёл пиво пить :)
27 апр 15, 13:40    [17569046]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
iap
Member

Откуда: Москва
Сообщений: 46999
LexusR
alter table dbo.t add constraint ck_1 check(isnull(id1,id2)=isnull(id2,id1));
Тогда пропустит id1 IS NULL AND id2 IS NULL
27 апр 15, 13:42    [17569055]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
invm
Member

Откуда: Москва
Сообщений: 9396
alter table dbo.t add constraint ck_1 check(id1 + id2 is null);
:)
27 апр 15, 13:45    [17569079]     Ответить | Цитировать Сообщить модератору
 Re: Триггер  [new]
iap
Member

Откуда: Москва
Сообщений: 46999
invm
alter table dbo.t add constraint ck_1 check(id1 + id2 is null);

:)
Оба NULLа пропустит.

Почему по-простому не написать
id1 IS NULL AND id2 IS NOT NULL OR id1 IS NOT NULL AND id2 IS NULL OR id1<>id2
???
27 апр 15, 13:50    [17569113]     Ответить | Цитировать Сообщить модератору
Топик располагается на нескольких страницах: [1] 2 3   вперед  Ctrl      все
Все форумы / Microsoft SQL Server Ответить