Недавно мы обнаружили проблему с производительностью одной из наших систем, и я думаю, что у меня есть исправление, но я не уверен, что мое понимание верно.
В простейшей форме у нас есть таблица blah
, в которую мы накапливаем различные значения на основе ключевого поля. Базовая форма:
recdate date
rectime time
system varchar(20)
count integer
accum1 integer
accum2 integer
Аккумуляторов гораздо больше, чем они, но все они одной формы. Первичный ключ состоит из recdate
, rectime
и system
.
Когда значения собираются в таблицу, счетчик для данного recdate/rectime/system
увеличивается, а значения для этого ключа добавляются в накопители. Это означает, что средние значения могут быть получены с помощью accumN / count
.
Теперь у нас также есть вид на эту таблицу, указанный следующим образом:
create view blah_v (
recdate, rectime, system, count,
accum1,
accum2
) as select distinct
recdate, rectime, system, count,
value (case when count > 0 then accum1 / count end, 0),
value (case when count > 0 then accum2 / count end, 0)
from blah;
Другими словами, представление дает нам среднее значение аккумуляторов, а не суммы. Это также гарантирует, что мы не получим деление на ноль в тех случаях, когда число равно нулю (эти записи do существуют, и нам не разрешено их удалять, поэтому не говорите мне, что они Мусор - вы проповедуете в хоре).
Мы заметили, что разница во времени между выполнением:
select distinct recdate from XX
сильно зависит от того, используем ли мы таблицу или представление. Я говорю о разнице в 1 секунду для таблицы и 27 секунд для представления (с 100К строк).
Мы на самом деле отследили его до select distinct
. Кажется, что происходит то, что СУБД фактически загружает все строки и сортирует их, чтобы удалить дубликаты. Это достаточно справедливо, это то, что мы глупо сказали, чтобы это делало.
Но я вполне уверен, что тот факт, что представление включает в себя каждый компонент первичного ключа, означает, что в любом случае невозможно иметь дубликаты. Мы проверили проблему, поскольку, если мы создадим другое представление без отличного, оно будет работать с той же скоростью, что и базовая таблица.
Я просто хотел подтвердить мое понимание того, что select distinct
не может иметь дубликатов, если он включает все компоненты первичного ключа. Если это так, то мы можем просто соответствующим образом изменить вид.