Создание эффективной группировки Oracle / PL_SQL и временной запрос - PullRequest
0 голосов
/ 16 сентября 2011

Мне снова нужна помощь базы данных. Да Эффективность имеет большое значение.

У меня есть стол

Скажем так. где ID - это первичный ключ.

Id Activity Time 
1. Lunch     2:00
2. Lunch     1:00
4. Lunch     4:00
5. Meeting   1:00
6. Meeting   12:00
7. Meeting   3:00
8. break     1:00

Я бы хотел, чтобы запрос вернулся.

Каждое действие один раз с самым поздним временем.

Так что ответ будет.

4. Lunch   4:00
7. Meeting 3:00
8. break   1:00

Я сделал это с
Вложив, выберите, где я бы вернул всю таблицу, а затем выберите

first_value(table) over (partition by activity order by time desc)

Но я ищу более эффективный способ сделать это

Спасибо.

Да

select activity, max(time) from mytable group by activity

будет работать отлично, но это также убивает время, необходимое для извлечения данных, есть ли способ НАМНОГО быстрее?

Ответы [ 3 ]

2 голосов
/ 16 сентября 2011

Переписывание простых запросов, чтобы сделать их быстрее, почти никогда не является ответом. Вопрос, который вы хотите задать: «какие еще изменения я могу внести в базу данных, чтобы этот запрос ускорился?»

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

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


Ответ на комментарий: Вы можете создать индекс с синтаксисом, подобным create index ak_activities_id_activ_time (id, activity, time);. Чтобы понять, почему это поможет, вам нужно сначала понять некоторые основы базы данных.

Базы данных хранят данные таблиц без какой-либо организации. Если вы запрашиваете у таблицы конкретное значение, она буквально должна просмотреть каждую строку в таблице, чтобы узнать, содержит ли она это значение. Сводный запрос должен выполнить немного больше работы: он должен отсортировать данные по группам, а затем применить агрегатную функцию к соответствующим столбцам, чтобы найти ответ, который вы ищете.

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

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

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

Так почему бы вам не проиндексировать все? Ответ заключается в том, что индексы являются компромиссом. Хорошо разработанный индекс ускорит некоторые запросы, но каждый индекс будет занимать дисковое пространство и замедлять вставки и обновления (индекс должен быть изменен вместе с таблицей). Обычно это не слишком важно, но создание слишком большого числа индексов для таблицы приведет к заметным проблемам с производительностью.


Теперь, когда я объяснил некоторые основные понятия базы данных, у меня есть рекомендация: наймите кого-нибудь, кто знает, что он делает, для работы с вашей базой данных. Настройка баз данных - это совершенно другой набор навыков, нежели программирование, и просьба прикладного программиста выполнить эту работу обычно является пустой тратой времени и денег. Даже если это просто консультант, который может работать над конкретными проблемами, иметь кого-то, кто может получить доступ к вашей базе данных и понять теорию, лежащую в основе, будет гораздо продуктивнее, чем чувствовать себя в темноте.

1 голос
/ 16 сентября 2011
select max(id), activity, max(time) from yourTable group by activity

этого достаточно, если ваш стол организован так, как вы показали.однако, если ваши идентификаторы или время не являются последовательными, оно сломается.

1 голос
/ 16 сентября 2011
select activity, max(time) from mytable group by activity
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...