Главная страница
Top.Mail.Ru    Яндекс.Метрика
Текущий архив: 2007.02.25;
Скачать: CL | DM;

Вниз

Один к одному   Найти похожие ветки 

 
Гоблин   (2006-11-15 21:22) [0]

Привет

Собственно, как реализовать сабж? Про один ко многим всё понятно, а про сабж никак не могу найти.


 
Desdechado ©   (2006-11-15 21:32) [1]

Обычно это не нужно. Но если очень хочется, то в первой таблице PK, во второй FK на него + по этому же полю UNIQUE


 
Anatoly Podgoretsky ©   (2006-11-15 21:37) [2]

> Гоблин  (15.11.2006 21:22:00)  [0]

Ни чем физически не отличается от один ко многим, только каждой записи одной таблицы соответствует одна запись другой таблицы.
Обычно такая связь не нужна, поскольку проще объединить в одну таблицу.
Причиной использования могут быть физические ограничения.


 
atruhin ©   (2006-11-16 03:52) [3]

Ну почему это не нужно? Обычное наследование таблиц.
Пример:
таблица КОРРЕСПОНДЕНТЫ
           ФИЗ.ЛИЦА
           ЮР. ЛИЦА

Корреспонденты содержит общие поля, на нее FK от документов,
остальные детализация.
У нас вся система на подобном наследовании построенна.


 
ЮЮ ©   (2006-11-16 04:14) [4]


> то в первой таблице PK, во второй FK на него + по этому
> же полю UNIQUE



А почему не просто, во второй PK и FK на PK в первой ?


 
Desdechado ©   (2006-11-16 09:40) [5]

ЮЮ ©   (16.11.06 04:14) [4]
Сути это не меняет (если FK и PK в подчиненной таблице по той же самой комбинаци полей), однако в случае 1:1 мне "ближе и понятнее" все-таки UQ. Оно точнее отображает смысл, т.к. PK претендует на ведущую роль, а таблица все-таки подчиненная.


 
ЮЮ ©   (2006-11-16 09:44) [6]


> PK претендует на ведущую роль, а таблица все-таки подчиненная.

FK вполне умерит эти претензии :)


 
Anatoly Podgoretsky ©   (2006-11-16 10:29) [7]

> ЮЮ  (16.11.2006 09:44:06)  [6]

Но ПК может их расширить


 
Гоблин   (2006-11-16 21:11) [8]

Так что же лучше
FK+Union
или
PK?


 
Гоблин   (2006-11-16 21:12) [9]

Ой, что я написал?

UNIQUE


 
Desdechado ©   (2006-11-16 21:18) [10]

Если ты внимательно читаешь, то заметишь, что разговоры шли о PK vs UQ. FK в любом случае нужен.


 
Гоблин   (2006-11-16 22:23) [11]

А, ну понятно. Но что же лучше?


 
atruhin ©   (2006-11-17 04:29) [12]

Да что угодно, обычный холивар, типа Delphi vs C++


 
Гоблин   (2006-11-18 14:04) [13]

Ну ладно тогда, сэнкс.


 
Гоблин   (2006-11-18 17:58) [14]

Хм.

А я вот тут подумал. Что мне будет мешать вставить запись в системную таблицу без вставки соответствующей записи в подчинённую? То же самое с удалением.


 
Desdechado ©   (2006-11-18 20:19) [15]

Это уже задача триггера.
Ведь даже если это соединить в одну таблицу, ничто ведь не мешает заполнятьтолько часть полей.

ЗЫ кстати, есть еще OUTER JOIN, который позволяет в некоторых случаях не сильно заботиться о наличии записей в подчиненной таблице


 
Гоблин   (2006-11-18 20:48) [16]

В случае одной таблицы not null там, где это надо.


 
atruhin ©   (2006-11-18 20:59) [17]

> В случае одной таблицы not null там, где это надо.

Создаешь модифицируемое представление, на него права и ограничения,
на таблицы прав не даешь.


 
Гоблин   (2006-11-21 22:09) [18]

А вот в случае IB\FB в таких таблицах можно использовать один генератор на все таблицы или по отдельности? Или в системной таблице вообще на пологаться на автоинкремент, а брать ID из справочников?


 
atruhin ©   (2006-11-22 12:14) [19]

> Или в системной таблице вообще на пологаться на автоинкремент,
> а брать ID из справочников?

ничего не понятно


 
Desdechado ©   (2006-11-22 12:22) [20]

> А вот в случае IB\FB в таких таблицах можно использовать один генератор на все таблицы или по отдельности?
Без разницы. Но я предпочитаю каждой таблице по генератору (если в ней есть, чего нумеровать).


 
Гоблин   (2006-11-22 19:25) [21]

Ай, извиняюсь. Въехал.

Последний вопрос. Вставку записей сразу в две таблицы с FK между ними нельзя сразу сделать? Либо два запроса, либо через ХП. Я не прав?


> Desdechado ©   (18.11.06 20:19) [15]
> Это уже задача триггера.

А можно пример такого триггера? А то моя идея проверять все поля на предмет вставки мне что-то не нравится.


 
Desdechado ©   (2006-11-22 20:30) [22]

> Последний вопрос.
Операции строго последовательные, хоть сами по себе, хоть в ХП.

> пример такого триггера
например, в after insert-триггере на главную таблицу делать insert в подчиненную сразу


 
MsGuns ©   (2006-11-22 20:39) [23]

>Гоблин   (22.11.06 19:25) [21]
>Последний вопрос. Вставку записей сразу в две таблицы с FK между ними нельзя сразу сделать?

Можно. Для этого и существуют транзакции

>Либо два запроса, либо через ХП. Я не прав?

Для сервера в сущности все едино: выполняются ли две вставки в таблицы (или таблицу) двумя клиентскими запросами или в контексте одного скрипта (хранимки) двумя шагами, оформленными каждый как запрос.
Главное - все существующие стандарты сиквеля  не позволяют в одном SQL-операторе вносить изменения более чем в одну таблицу (И ЭТО ПРАВИЛЬНО !!!)


 
Гоблин   (2006-11-22 21:06) [24]

Т.е. этот триггер должен вставить не важно что в подчинённую таблицу - лишь бы вставил. Но как узнать ID текущей записи в главной таблице и передать в триггер? Можно ли для этого использовать значение генератора?

А как же быть с удалением? Я ж могу что-то удалить из справочника, а главная об этом ничего знать не будет.


 
Desdechado ©   (2006-11-22 21:17) [25]

У тебя каша в голове.
Справочник, этота таблица, НА которую ссылаются. Она же MASTER-таблица или главная.
Поэтому при удалении из главной в зависимости от того, как ты опишешь внешний ключ в подчиненной таблице,так и будет себя вести. Если с ON DELETE CASCADE, то удалятся записи и в подчиненной тоже. Если без CASCADE, то будет ошибка - надо сначала удалять записи из подчиненной, потом из главной.
Если же боишься удаления из подчиненной напрямую, напиши процедуру удаления, которая будет удалять сразу из двух таблиц. И дай процедуре право на удаление из этих таблиц. А у юзера отними права на удаление из этих таблиц напрямую.

> как узнать ID текущей записи в главной таблице и передать в триггер
В триггере и так доступны все поля строки той таблицы, на которую он сработал. Читай LangRef.pdf


 
Гоблин   (2006-11-23 20:03) [26]


> В триггере и так доступны все поля строки той таблицы, на
> которую он сработал. Читай LangRef.pdf


Это случаем не OLD и NEW?


 
atruhin ©   (2006-11-24 06:22) [27]

Да, они


 
Гоблин   (2006-11-24 17:44) [28]

А как бы тогда значение ID на клиента переслать?


 
Гоблин   (2006-11-25 19:17) [29]

А вот такая хранимка будет работать или нет


CREATE TABLE CATALOG
(
 ID INTEGER NOT NULL,
 Name   VARCHAR(50) CHARACTER SET WIN1251 NOT NULL,
 Object_type SMALLINT NOT NULL,
PRIMARY KEY (ID)
);

CREATE TABLE TREE
(
 ID INTEGER NOT NULL,
 Sys_ID INTEGER NOT NULL,
 SysParent_ID  INTEGER NOT NULL,
PRIMARY KEY (ID),
CONSTRAINT RTREE FOREIGN KEY (Sys_ID) REFERENCES CATALOG (ID),
CONSTRAINT RTREEPARENTSYS FOREIGN KEY (SysParent_ID) CATALOG (ID)
);

CREATE PROCEDURE SETNAMES (parent_ID INTEGER, Name_ Varchar(20), Table SMALLINT)
RETURNS (DID INTEGER)
AS
BEGIN
SET TRANSACTION;
INSERT INTO CATALOG (Name, Object_type) VALUES ("(dummy)", :Table);
SELECT C.ID FROM CATALOG C WHERE C.Name = "(dummy)" INTO :DID;
INSERT INTO TREE (Sys_ID, SysParent_ID) VALUES (:DID, :parent_ID);
UPDATE CATALOG SET Name = :Name_ WHERE ID = :DID;
COMMIT;
END


 
atruhin ©   (2006-11-25 20:18) [30]

> А вот такая хранимка будет работать или нет

SET TRANSACTION;,COMMIT; - лишнии, вроде даже не скомпилируется, но
в любом случае, управлять транзакциями в процедурах нельзя.
Вообще должно быть примерно так:

CID = gen_id(GEN_CATALOG_ID, 1);
INSERT INTO CATALOG (ID, Name, Object_type) VALUES (:CID, :NAME_, :Table);
INSERT INTO TREE (Sys_ID, SysParent_ID) VALUES (:CID, :parent_ID);


 
atruhin ©   (2006-11-25 20:20) [31]

А еще лучше сходить на www.ibase.ru
Там прочитать ВСЕ статьи, в них найдешь ответы на все твои вопросы.


 
Гоблин   (2006-11-25 21:19) [32]

А, т.е. процедуру запускать в контексте транзакции с клиента?
С ibase.ru выкачал всё, что можно, и что нельзя.
Для FB 2.0 проще, наверное, будет так

CREATE PROCEDURE SETNAMES (parent_ID INTEGER, Name_ Varchar(20), Table SMALLINT)
RETURNS (DID INTEGER)
AS
BEGIN
INSERT INTO CATALOG (Name, Object_type) VALUES (:Name_, :Table) RETURNING ID INTO :DID;
INSERT INTO TREE (Sys_ID, SysParent_ID) VALUES (:DID, :parent_ID);
END


А инкремент ID через триггер.


 
MsGuns ©   (2006-11-25 23:15) [33]

>atruhin ©   (25.11.06 20:18) [30]
>но в любом случае, управлять транзакциями в процедурах нельзя.

Вы уверены в этом ?


 
atruhin ©   (2006-11-26 00:52) [34]

> Вы уверены в этом ?

Ну с поправкой, что мы говорим о FB, то уверен.


 
Гоблин   (2006-11-30 20:16) [35]

Ну ладно, ещё раз спасибо.
Всех целую.



Страницы: 1 вся ветка

Текущий архив: 2007.02.25;
Скачать: CL | DM;

Наверх




Память: 0.55 MB
Время: 0.078 c
15-1170314724
=Teddy=
2007-02-01 10:25
2007.02.25
Откуда скачать Indy 10 для Delphi 5 !!!


1-1168220567
Sleepeer
2007-01-08 04:42
2007.02.25
Перехват процесса выполнения определённых функций из чужой DLL


15-1170353475
VolJinn
2007-02-01 21:11
2007.02.25
Программы для блюджекинга на кпк


2-1170638798
Новичек
2007-02-05 04:26
2007.02.25
Динамический массив объектов.


11-1143716182
Боб
2006-03-30 14:56
2007.02.25
Архив конференции KOL