powered by simpleCommunicator - 2.0.37     © 2025 Programmizd 02
Форумы / SQLite [игнор отключен] [закрыт для гостей] / Триггер для обновления числа записей
7 сообщений из 7, страница 1 из 1
Триггер для обновления числа записей
    #39307071
amsdev
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Приветствую !

Помогите новичку ) Есть таблица Groups которая содержит список под-таблиц с контактами:

Код: sql
1.
2.
3.
4.
5.
6.
CREATE TABLE Groups (
    ID  INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,
    ListName  VARCHAR (100),
    ContactsCount INTEGER  DEFAULT (0),
    ContactsTableName VARCHAR (20)
);



2. Contacts - таблица контактов:

Код: sql
1.
2.
3.
4.
CREATE TABLE List1 (
    ID INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,
    ContactName VARCHAR (100) NOT NULL
);



Добавляем списки контактов в таблицу Groups:

Код: sql
1.
2.
INSERT INTO Groups (Name, ContactsTableName) VALUES ('Список контактов 1', 'List1');
INSERT INTO Groups (Name, ContactsTableName) VALUES ('Список контактов 2', 'List2');



Проблема вот в чем: в под-таблицах List1, List2 и т.д. может быть по несколько миллионов записей (контактов). При этом контакты могут массово добавляться или удаляться таким образом:

Код: sql
1.
2.
3.
4.
5.
START TRANSACTION;
INSERT INTO List1 (ContactName) VALUES ('Ivan Ivanov');
INSERT INTO List1 (ContactName) VALUES ('Petr Petrov');
... еще 1000 инсертов
COMMIT;



Аналогичным образом контакты будут массово удаляться через DELETE.

Встает вопрос: как поддерживать актуальным значения поля ContactsCount в таблице Groups ? SELECT COUNT (*) FROM List1 будет тормозить тем больше чем больше записей в таблице, а таблиц контактов может быть много ! В этой связи хотелось бы сделать триггер, который будет обновлять значение поле ContactsCount после выполнения транзакций на удаление или добавление.

Можно ли сделать триггер, который сработает ОДИН раз после транзакции, содержащей 1000 INSERT'ов (или DELETE'ов) ? Который сделает что-то типа этого:

Код: sql
1.
UPDATE Groups SET ContactsCount=ContactsCount+Insert_Transaction_Rows_Affected WHERE ContactsTableName=Insert_Transaction_Table_Name


При этом хотелось бы чтобы триггер срабатывал один раз после транзакции, а не 1000 раз для каждого INSERT'a в транзакции, иначе массовая вставка или удаление будут адски тормозить.

Возможно как-то решить эту проблему ? Я думаю это типовая задача и наверняка с ней кто-то сталкивался )

Огромное спасибо за помощь !
...
Рейтинг: 0 / 0
Триггер для обновления числа записей
    #39307074
Фотография VSVLAD
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
amsdev,

Почему бы не использовать "классическую" схему (хранить все записи контактов в одной таблице, а не дробить на несколько)?
Groups (Group_id, Name)
Contacts (Contract_id, Group_id, Name)

А на счёт триггера, тогда можно и без него будет. Просто выбрать Count всех записей, сгруппированных по Group_Id. Тысяча инсертов, это немного. Выборка быстрая будет
...
Рейтинг: 0 / 0
Триггер для обновления числа записей
    #39307076
amsdev
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
авторПочему бы не использовать "классическую" схему (хранить все записи контактов в одной таблице, а не дробить на несколько)?
Groups (Group_id, Name)
Contacts (Contract_id, Group_id, Name)


Потому что списки могут удаляться и DROP TABLE (по идее) отработает быстрее чем DELETE FROM AllLists WHERE GroupID=x

авторТысяча инсертов, это немного. Выборка быстрая будет

Миллионы INSET'ов или DELETE'ов, разбитые на транзакции по 1000.
...
Рейтинг: 0 / 0
Триггер для обновления числа записей
    #39307090
White Owl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
amsdev ContactsTableName VARCHAR (20)
За это надо отрывать руки, ноги и все остальные выступающие части тела.

amsdevПри этом хотелось бы чтобы триггер срабатывал один раз после транзакции, а не 1000 раз для каждого INSERT'a в транзакцииНельзя. В сегодняшней версии SQLite триггер отрабатывает для каждой строки.
Триггер на транзакцию лежит в планах на разработку уже несколько лет.
Читать тут и тут:
http://sqlite.org/lang_createtrigger.html
http://sqlite.org/omitted.html

amsdevиначе массовая вставка или удаление будут адски тормозить.

Возможно как-то решить эту проблему ? Я думаю это типовая задача и наверняка с ней кто-то сталкивался )
Простой update агрегирующей таблицы после редактирования ведомой таблицы.
Но не сработает в имеющейся схеме.
...
Рейтинг: 0 / 0
Триггер для обновления числа записей
    #39307093
amsdev
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Хреново конечно, придется ручками считать и обновлять после выполнения транзакций...

авторContactsTableName VARCHAR (20)

авторЗа это надо отрывать руки, ноги и все остальные выступающие части тела.

За что ? ) В чем преступление ?
...
Рейтинг: 0 / 0
Триггер для обновления числа записей
    #39307095
amsdev
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Уточню: я планирую реализовать эту схему (где каждый список лежит в отдельной таблице) потому что у меня возможны операции Удалить список и Очистить список (т.е. удалить все записи в списке, в котором может быть несколько миллионов записей). Хотелось бы избежать DELETE для миллионов записей и заменить его на DROP TABLE->CreateTable. Собственно, эта схема предполагается именно по этой причине.
...
Рейтинг: 0 / 0
Триггер для обновления числа записей
    #39307148
White Owl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
amsdevХреново конечно, придется ручками считать и обновлять после выполнения транзакций...

авторContactsTableName VARCHAR (20)

авторЗа это надо отрывать руки, ноги и все остальные выступающие части тела.

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

В любом случае, миллион записей за раз это, во первых, не так уж много.
Во вторых, это не может быть частой операцией. И задержка в несколько секунд не сделает погоды.
А в третьих я очень сомневаюсь что ты нам сказал реальные цифры. Не, есть конечно задачи в которых огромные объемы постоянно проходят через СУБД, но в этих задачах не бывает новичков :)
...
Рейтинг: 0 / 0
7 сообщений из 7, страница 1 из 1
Форумы / SQLite [игнор отключен] [закрыт для гостей] / Триггер для обновления числа записей
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]