|
|
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
Если я объединяю в представлении данные из двух проиндексированных таблиц (UNION), а потом в конструкции where ... использую это представление, то наблюдается тормоз... Индексы не работают? Как этого избежать? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 05.08.2002, 15:05:13 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
Саму вьюху проиндексировать не получится. union для indexed view запрещен. Можно перед обработкой всю вьюху сливать во временную таблицу и индексировать ее. Можно сделать отдельную табличку с полями, общими для двух таблиц на которые повесить нужные триггера. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 05.08.2002, 15:21:38 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
Если в двух таблицах нет и не может быть схожих записей, то вместо UNION необходимо использовать UNION ALL. При таком объединении не будет попарно производиться сравнение всех записей из этих таблиц для выявления повторяющихся записей (изкоторых пир использовании UNION необходимо включить в результирующий набор только одну копию). И работать все будет гораздо быстрее. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 05.08.2002, 15:56:02 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
согласен с Garya... на таком принципе обычно стороятся хранилища..... ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 05.08.2002, 16:55:14 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
Спасибо, Garya, последовал Вашему совету, но, к сожалению, быстродействие не увеличилось. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 05.08.2002, 17:48:27 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
покажите структуру с индексами и текст вью... ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 05.08.2002, 17:53:57 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
Ух, не знаю, захочет ли кто-нибудь прочитать столько кода, но все-таки: Текст вьюхи с UNION: Prihod Код: plaintext 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. Текст второй вьюхи с UNION: Rashod Код: plaintext 1. 2. 3. 4. 5. 6. 7. А вот кусок текста триггера, в котором используются предыдущие вьюхи: Код: plaintext 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. 16. 17. 18. 19. 20. 21. 22. 23. 24. 25. 26. 27. 28. 29. 30. 31. 32. 33. 34. 35. Все таблицы проиндексированы по полям, присутствующим в Where триггера Так вот, триггер обрабатывает одну запись ~ 2 секунды! Это сильно портит жизнь. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 06.08.2002, 11:07:51 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
> Все таблицы проиндексированы по полям, присутствующим в Where триггера... Присутствовать-то они там присутствуют, да только внутри вычисляемого выражения IsNul(...). А это приводит к неиспользованию индексов и полному сканированию таблицы. А если учесть еще и такое количество подзапросов с агрегатными функциями, то можно удивляться, что ты вообще можешь дождаться, когда все это отработает. Нужно кардинально все это хозяйство переделывать. Нужно кумекать. Как вариант, завести вспомогательную таблицу для итогов/подитогов и триггерами на модификацию этих самых приходов/расходов туда прибавалять итоги. Механиз транзакций гарантирует целостность и соответствие содержимого этой таблицы содержимому таблиц приходов/расходов. Избавишься от агрегатных функций. А для начала просто вызови VIEW из QA и засеки время - сколько он открывается. IMHO, проблема не во VIEW, а в триггере. P.S. Если в триггере используются к тому же временные таблицы (либо табличные переменные), то триггер компилируется при каждом вызове, на что уходит дополнительное время. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 06.08.2002, 12:01:15 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
2 Garya: Убрал IsNull(), время обработки не уменьшилось. View открывается 16 секунд. 43000 строк. Не знаю, много это или мало ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 06.08.2002, 15:18:40 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
а что показывает план запроса на вьюхах? ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 06.08.2002, 15:38:10 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
Правильно не изменилось. IsNull как раз почти не тормозит. Я бы сказал "совсем не тормозит", но не было случая проверить ВСЕ варианты. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 06.08.2002, 15:46:02 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
2 MiCe: Слева - направо, сверху - вниз Select Cost: 0% Concatenation 0% Compute Scalar 0% Table Scan 32% Filter 1% Table scan 12% Bookmark Lookup 9% Nested Loops/Inner join 0% Bookmark Lookup 38% Nested Loops/Inner join 0% Table Scan 4% WaybillDetail... Что-то там про Index seek 2% Waybill... Index seek 1% ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 06.08.2002, 16:17:01 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
помоему при таком количестве он вьхи засовывает в темптабл.... ща еще подемаю... ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 06.08.2002, 16:31:55 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
У тебя слишком много агрегатных функций, каждая из которых вычисляется отдельным сканированием. Попробуй уменьшить количество подзапросов и/или агрегатных функций. Мне, в частности, не понятно, зачем в первом подзапросе нужно вычислять приходы ДО текущей дате (по условию <), а во втором отдельно приходы по текущей дате (по условию =). Нельзя их как-нибудь объединить в один подзапрос по условию <=? А вот если приходы и расходы хранить вообще в одной таблице, то вместо всей груды подзапросов достаточно вообще одного, у которого внутри summ() находится case, который приходы суммирует с плюсом, а расходы - с минусом. Если этот вариант не нравится, обрати внимание на еще одно решение, предложенное в моем предыдущем постинге (с триггерами, отслеживающими итоговые данные). ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 06.08.2002, 17:33:59 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
2 Garya: >Мне, в частности, не понятно, зачем в первом подзапросе нужно вычислять приходы ДО текущей дате (по условию <), а во втором отдельно приходы по текущей дате (по условию =). Нельзя их как-нибудь объединить в один подзапрос по условию <=? К сожалению, нельзя. В поле Date хранится только дата, без времени, записей с одинаковой датой может быть несколько, а нужно как-то выбирать записи до текущей. Вот и пришлось извратиться, используя 2 подзапроса: в первом выбираются записи с датой меньше текущей, а во втором - записи с датой, соответствующей текущей, но с ID, меньшим либо равным, чем у текущей записи. Приходы и расходы хранить в одной таблице вообще нельзя: Приходами у меня считаются поступления денег, поступления товара (входящие накладные), уценки. Это естественно все разные таблицы. Расходы - деньги, товар (исходящие накладные). Входящие и исходящие накладные лежат в одной таблице, Входящие и исходящие деньги - тоже в одной таблице. Пихать накладные и деньги в одну таблицу - я думаю не стоит. >Как вариант, завести вспомогательную таблицу для итогов/подитогов и триггерами на модификацию этих самых приходов/расходов туда прибавалять итоги. Так это я и делаю! В таблице Waybill (Накладные) я в поле PaymentDate сохраняю дату оплаты накладной. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 06.08.2002, 18:00:17 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
> ...в первом выбираются записи с датой меньше текущей, а во втором - записи с датой, соответствующей текущей, но с ID, меньшим либо равным, чем у текущей записи... Так, может, дата воббще не нужна!? Достаточно одного ID? > Так это я и делаю! В таблице Waybill (Накладные) я в поле PaymentDate сохраняю дату оплаты накладной Я не про дату, а про сумму. Для того чтобы не писать select sum(Prohod.Summa) form Prihod, можно завести вспомогательную таблицу, в которой триггерами на Insert/update/delete, прицепленными к таблице Prihod , получать эту самую сумму. А в том скрипте, который изображен, использовать простой select SumFld from AddTable where ... ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 06.08.2002, 18:22:36 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
2 Garya: >Так, может, дата воббще не нужна!? Достаточно одного ID? К сожалению, нужна. Ведь не обязательно у накладной с меньшей датой меньший ID. Юзер может создать накладную на послезавтра (ID=1), а потом на завтра(ID=2). Специфика задачи. >Я не про дату, а про сумму. Для того чтобы не писать select sum(Prohod.Summa) form Prihod, можно завести вспомогательную таблицу, в которой триггерами на Insert/update/delete, прицепленными к таблице Prihod, получать эту самую сумму. А в том скрипте, который изображен, использовать простой select SumFld from AddTable where ... А это мысль. Действительно, чего это я сумму каждый раз пересчитываю? С меня пиво. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 07.08.2002, 10:59:42 |
|
||
|
Индексы и UNION
|
|||
|---|---|---|---|
|
#18+
Зря это все сведено в один запрос... я бы развел это все по нескольким ... При "разведении" и в голове бы все это уложилось более правильно и в процедуре бы "гладко" стало. PS Одним словом не ремонтировать а переписать надо ... при ремонте большого уменьшения времени выполнения не будет. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 07.08.2002, 11:50:46 |
|
||
|
|

start [/forum/topic.php?fid=46&msg=32041260&tid=1821320]: |
0ms |
get settings: |
6ms |
get forum list: |
13ms |
check forum access: |
2ms |
check topic access: |
2ms |
track hit: |
44ms |
get topic data: |
7ms |
get forum data: |
2ms |
get page messages: |
49ms |
get tp. blocked users: |
1ms |
| others: | 206ms |
| total: | 332ms |

| 0 / 0 |
