Модераторы: skyboy
  

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Уникальная комбинация полей 
:(
    Опции темы
Ripper
Дата 18.12.2011, 13:07 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Lonely soul...
**


Профиль
Группа: Участник
Сообщений: 920
Регистрация: 30.6.2004
Где: г. Москва

Репутация: нет
Всего: 23



Здравствуйте.
У меня есть таблица предложений контрактов, где есть такие поля:
ID, proposer, target, contract_type, date. 

Как грамотнее написать запрос на добавление строки в таблицу, чтобы пара proposer, target оказалась уникальной? Т.е. если такие два значения уже существуют, то не добавлять запись? 

На ум приходит написать что-то вроде insert into contract_suggestion (proposer, target, contract_type, date) values (...) where not exists (select * from contract_suggestion where (proposer={$proposer} and  target={$target})  или как-то так. А, и еще пара должна быть уникальна с обоих сторон, т.е. не должно быть скажем двух пар: 2,5 и 5,2. Но я думаю есть более хорошее решение.

Спасибо заранее.



--------------------
"Он знает: надо смеяться над тем, что тебя мучит, иначе не сохранишь равновесия, иначе мир сведет тебя с ума" - Над кукушкиным гнездом
PM MAIL ICQ   Вверх
Zloxa
Дата 18.12.2011, 17:52 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Чо?
****


Профиль
Группа: Завсегдатай
Сообщений: 3473
Регистрация: 12.9.2008

Репутация: 33
Всего: 161



Добавить ограничение уникальности (unique constraint) по паре (proposer, target).
Другие способы обеспечения уникальности - от лукавого.


--------------------
Достоверно известно, что 89% людей доверяют статистике взятой с потолка smile
PM   Вверх
Ripper
Дата 19.12.2011, 02:10 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Lonely soul...
**


Профиль
Группа: Участник
Сообщений: 920
Регистрация: 30.6.2004
Где: г. Москва

Репутация: нет
Всего: 23



Да, а вот если в случае что пара должна быть уникальна в обоих комбинациях? Например если есть 5,3 то 3,5 уже не должно быть?
В интернете нашел пример с триггером, вроде помогло)


--------------------
"Он знает: надо смеяться над тем, что тебя мучит, иначе не сохранишь равновесия, иначе мир сведет тебя с ума" - Над кукушкиным гнездом
PM MAIL ICQ   Вверх
Akina
Дата 19.12.2011, 08:04 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Советчик
****


Профиль
Группа: Модератор
Сообщений: 20581
Регистрация: 8.4.2004
Где: Зеленоград

Репутация: 106
Всего: 454



Цитата(Ripper @  19.12.2011,  03:10 Найти цитируемый пост)
Например если есть 5,3 то 3,5 уже не должно быть?

Ввести constraint на уникальность CONCAT(MIN(proposer, target), MAX(proposer, target))


--------------------
 О(б)суждение моих действий - в соответствующей теме, пожалуйста. Или в РМ. И высшая инстанция - Администрация форума.

PM MAIL WWW ICQ Jabber   Вверх
Zloxa
Дата 19.12.2011, 08:47 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Чо?
****


Профиль
Группа: Завсегдатай
Сообщений: 3473
Регистрация: 12.9.2008

Репутация: 33
Всего: 161



Akina, маська умеет строить ключи по функции? smile 

Цитата(Ripper @  19.12.2011,  02:10 Найти цитируемый пост)
 нашел пример с триггером

Крайне рекомендую внимательно протестировать работу этого триггера в многопользовательском режиме, в разных режимах изоляции транзакций.  smile 


--------------------
Достоверно известно, что 89% людей доверяют статистике взятой с потолка smile
PM   Вверх
Akina
Дата 19.12.2011, 09:10 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Советчик
****


Профиль
Группа: Модератор
Сообщений: 20581
Регистрация: 8.4.2004
Где: Зеленоград

Репутация: 106
Всего: 454



Цитата(Zloxa @  19.12.2011,  09:47 Найти цитируемый пост)
маська умеет строить ключи по функции?

Нет. Но, как всегда, есть путь через задний проход...
Вводится доп. поле. На него накладывается ограничение уникальности. Поле напрямую нигде не используется, заполняется или изменяется в триггере. При нарушении уникальности срабатывает ограничение, и отваливается весь запрос.

Код

mysql> create table test (val int, val2 int);
Query OK, 0 rows affected (0.13 sec)

mysql> select * from test;
Empty set (0.00 sec)

mysql> delimiter @@
mysql> create trigger add_val2 before insert on test
    -> for each row begin
    -> set new.val2 = 5;
    -> end;
    -> @@
Query OK, 0 rows affected (0.03 sec)

mysql> delimiter ;

mysql> insert into test(val) values (1),(2);
Query OK, 2 rows affected (0.03 sec)
Records: 2  Duplicates: 0  Warnings: 0

mysql> select * from test;
+------+------+
| val  | val2 |
+------+------+
|    1 |    5 |
|    2 |    5 |
+------+------+
2 rows in set (0.00 sec)

mysql>

В примере val2 - как раз такое поле, заполняемое из триггера неявно. Наложите на него UNIQUE - и при дублировании вставка строк обломится. 
Код

mysql> delete from test;
Query OK, 2 rows affected (0.01 sec)

mysql> create unique index unique_val2 on test(val2);
Query OK, 0 rows affected (0.14 sec)
Records: 0  Duplicates: 0  Warnings: 0

mysql> select * from test;
Empty set (0.00 sec)

mysql> insert into test(val) values (1),(2);
ERROR 1062 (23000): Duplicate entry '5' for key 1

mysql> select * from test;
Empty set (0.00 sec)

mysql> insert into test(val) values (1);
Query OK, 1 row affected (0.02 sec)

mysql> insert into test(val) values (2);
ERROR 1062 (23000): Duplicate entry '5' for key 1

mysql> select * from test;
+------+------+
| val  | val2 |
+------+------+
|    1 |    5 |
+------+------+
1 row in set (0.00 sec)

mysql>

Аналогично создаётся и триггер before update.

Поскольку мы работаем исключительно с таблицей NEW - нам не страшны никакие многопользовательские заморочки. Или, вернее, так - мы не получим никаких ДОПОЛНИТЕЛЬНЫХ граблей.


Это сообщение отредактировал(а) Akina - 19.12.2011, 09:15


--------------------
 О(б)суждение моих действий - в соответствующей теме, пожалуйста. Или в РМ. И высшая инстанция - Администрация форума.

PM MAIL WWW ICQ Jabber   Вверх
Zloxa
Дата 19.12.2011, 09:48 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Чо?
****


Профиль
Группа: Завсегдатай
Сообщений: 3473
Регистрация: 12.9.2008

Репутация: 33
Всего: 161



Цитата(Akina @  19.12.2011,  09:10 Найти цитируемый пост)
Нет. Но, как всегда, есть путь через задний проход...

Я спросил никак не потому, что хотел там подколоть или что-то вроде, но потому, что оракл умеет. Плюс и оракл и ms поддерживают вычисляемые столбцы, на которые тоже можно накладывать ограничения.

Цитата(Akina @  19.12.2011,  09:10 Найти цитируемый пост)
Поскольку мы работаем исключительно с таблицей NEW - нам не страшны никакие многопользовательские заморочки. Или, вернее, так - мы не получим никаких ДОПОЛНИТЕЛЬНЫХ граблей.

Да, при такой реализации все должно быть нормуль. Ограничение контролируется уникальным ключом. Я предостережение оставлял на случай, если ТС замутил реализацию контроля уникальности не ключом а триггером. Типа выбирается из таблы по значению ключа и поднимает исключение, если нашел задвоения.


--------------------
Достоверно известно, что 89% людей доверяют статистике взятой с потолка smile
PM   Вверх
Akina
Дата 19.12.2011, 10:20 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Советчик
****


Профиль
Группа: Модератор
Сообщений: 20581
Регистрация: 8.4.2004
Где: Зеленоград

Репутация: 106
Всего: 454



Цитата(Zloxa @  19.12.2011,  10:48 Найти цитируемый пост)
Я спросил никак не потому, что хотел там подколоть или что-то вроде

Я знаю.



--------------------
 О(б)суждение моих действий - в соответствующей теме, пожалуйста. Или в РМ. И высшая инстанция - Администрация форума.

PM MAIL WWW ICQ Jabber   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
1 Пользователей читают эту тему (1 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | MySQL | Следующая тема »


 




[ Время генерации скрипта: 0.0879 ]   [ Использовано запросов: 21 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.