1️⃣Использование EXPLAIN для анализа запросов
2️⃣Продвинутые стратегии индексирования
├── Пересмотр покрывающих индексов
├── Частичные индексы для отфильтрованных данных
└── Стратегии индексирования для соединений
3️⃣Переписывание и оптимизация запросов
├── Пересмотр подзапросов к JOIN'ам
├── Общие табличные выражения (CTE) и рекурсивные запросы
└── Ограничение наборов результатов с помощью OFFSET-FETCH
4️⃣Денормализация данных для повышения производительности
├── Выбор кандидатов на денормализацию
├── Создание денормализованных таблиц
└── Баланс между согласованностью данных и производительностью
5️⃣Использование временных таблиц для оптимизации запросов
├── Временные таблицы для промежуточных результатов
├── Создание и наполнение временных таблиц
└── Временные таблицы и агрегации
6️⃣Оптимизация подзапросов и агрегаций
├── Оптимизация подзапросов
└── Оптимизация агрегаций
7️⃣Избегайте курсоров и циклов для повышения производительности
├── Операции на основе множеств
├── Пакетная обработка
└── Оптимизация циклов с помощью операций на основе множеств
Примеры некоторых из этих приёмов
Пересмотр подзапросов к JOIN'ам.
Оригинальный подзапрос:
SELECT * FROM employees
WHERE department_id IN (SELECT department_id FROM departments WHERE region = 'West');
Переписан с использованием JOIN:
SELECT e.* FROM employees e
INNER JOIN departments d ON e.department_id = d.department_id
WHERE d.region = 'West';
Общие табличные выражения (CTE) предоставляют удобный способ упростить сложные запросы и улучшить их читаемость:
WITH RecursiveCTE AS (
SELECT employee_id, first_name, manager_id, 0 AS depth
FROM employees
WHERE manager_id IS NULL
UNION ALL
SELECT e.employee_id, e.first_name, e.manager_id, rc.depth + 1
FROM employees e
INNER JOIN RecursiveCTE rc ON e.manager_id = rc.employee_id
)
SELECT * FROM RecursiveCTE;
➖ Более подробно можно прочитать тут
@sqlhub