added theory bd b-tree and hash indexes
This commit is contained in:
@@ -0,0 +1,104 @@
|
|||||||
|
- Задание 1:
|
||||||
|
|
||||||
|
**Дана таблица:**
|
||||||
|
|
||||||
|
users(id PK, email, age, created_at)
|
||||||
|
|
||||||
|
|
||||||
|
**И индекс:**
|
||||||
|
|
||||||
|
CREATE INDEX idx_users_email ON users(email);
|
||||||
|
|
||||||
|
|
||||||
|
**Ответь для каждого варианта:**
|
||||||
|
|
||||||
|
- будет ли использоваться этот индекс;
|
||||||
|
- если нет — что нужно изменить (индекс или запрос).
|
||||||
|
|
||||||
|
**Варианты:**
|
||||||
|
|
||||||
|
1. SELECT * FROM users WHERE email = 'test@example.com'; // будет, менять ничего не нужно
|
||||||
|
2. SELECT * FROM users WHERE LOWER(email) = 'test@example.com'; // не будет, нужно изменить запрос, а именно убрать функцию LOWER
|
||||||
|
3. SELECT * FROM users WHERE email LIKE 'alex%'; // будет, все норм
|
||||||
|
4. SELECT * FROM users WHERE email LIKE '%@gmail.com'; // не будет, так как ищем оканчание строки. не знаю что тут можно поменять, как-будто ничего
|
||||||
|
5. SELECT * FROM users ORDER BY email LIMIT 10; // будет, все норм
|
||||||
|
6. SELECT * FROM users WHERE age BETWEEN 20 AND 30; // будет, все норм, но только B-tree
|
||||||
|
- Задание 2:
|
||||||
|
|
||||||
|
**Дана таблица заказов:**
|
||||||
|
|
||||||
|
orders(
|
||||||
|
id PK,
|
||||||
|
user_id,
|
||||||
|
status,
|
||||||
|
created_at,
|
||||||
|
amount
|
||||||
|
);
|
||||||
|
|
||||||
|
**К каждому запросу нужно сказать, что индекс не нужен/бесполезен):**
|
||||||
|
|
||||||
|
1. История заказов пользователя за период:
|
||||||
|
|
||||||
|
SELECT *
|
||||||
|
FROM orders
|
||||||
|
WHERE user_id = 123
|
||||||
|
AND created_at BETWEEN '2025-01-01' AND '2025-02-01'
|
||||||
|
ORDER BY created_at;
|
||||||
|
|
||||||
|
|
||||||
|
2. Ежедневная агрегация по статусу:
|
||||||
|
|
||||||
|
SELECT date_trunc('day', created_at) AS day,
|
||||||
|
status,
|
||||||
|
count(*)
|
||||||
|
FROM orders
|
||||||
|
GROUP BY day, status;
|
||||||
|
|
||||||
|
|
||||||
|
3. Проверка наличия хотя бы одного «висящего» заказа:
|
||||||
|
|
||||||
|
SELECT 1
|
||||||
|
FROM orders
|
||||||
|
WHERE status = 'pending'
|
||||||
|
LIMIT 1;
|
||||||
|
|
||||||
|
**Напиши `CREATE INDEX ...` и объясни, почему такой порядок колонок**
|
||||||
|
1. CREATE INDEX idx_orders_user_id_created_at ON orders (user_id, created_at)
|
||||||
|
ТАК ЭФФЕКТИВНЕЕ ПОТОМУ ЧТО СНАЧАЛА НАХОДИТСЯ ПОЛЬЗОВАТЕЛЕЙ, А ПОТОМ ДИАПАЗОН ЕГО ДАТ. ИНАЧЕ ПРИШЛОСЬ БЫ СНАЧАЛА ФИЛЬТРОВАТЬ ДИАПАЗОН ДАТ, А ПОТОМ НЕ НУЖНЫХ ПОЛЬЗОВАТЕЛЕЙ.
|
||||||
|
|
||||||
|
2. В ДАННОМ СЛУЧАЕ ИНДЕКС НЕ НУЖЕН ПОТОМУ ЧТО НЕТ УСЛОВИЯ В КОДЕ, ПОСТГРЕ ПРИДЕТСЯ В ЛЮБОМ СЛУЧАЕ СМОТРЕТЬ ВСЮ ТАБЛИЦУ.
|
||||||
|
|
||||||
|
3. CREATE INDEX idx_status_peding ON orders (status) WHERE status = 'pending'
|
||||||
|
ЗДЕСЬ МОЖНО ИСПОЛЬЗОВАТЬ ИНДЕКС ТОЛЬКО ПО ОДНОМУ ПОЛЮ "pending" ЧТОБЫ НЕ ИНДЕКСИРОВАТЬ ВСЕ ЗНАЧЕНИЯ ПО ДАННОМУ СТОЛБЦУ status
|
||||||
|
|
||||||
|
|
||||||
|
- Задание 3:
|
||||||
|
|
||||||
|
Та же таблица `orders`
|
||||||
|
|
||||||
|
**Выбери тип индекса и объясни почему выбрал такой для вариантов:**
|
||||||
|
|
||||||
|
1. SELECT * FROM orders WHERE id = 100500; // hash , возможное соединение таблиц
|
||||||
|
2. SELECT * FROM orders WHERE status = 'paid'; // спорен
|
||||||
|
3. SELECT * FROM orders WHERE created_at BETWEEN ...; // только B-tree из-за диапазона
|
||||||
|
4. SELECT * FROM orders WHERE user_id = 123; // hash, возможное соединение таблиц
|
||||||
|
|
||||||
|
**Вопросы:**
|
||||||
|
|
||||||
|
- Где hash имел бы смысл?
|
||||||
|
- Где обязательно B‑tree?
|
||||||
|
- Где индекс вообще спорен?
|
||||||
|
- Задание 4:
|
||||||
|
|
||||||
|
**Исходные индексы:**
|
||||||
|
|
||||||
|
CREATE INDEX idx_orders_user_created ON orders(user_id, created_at);
|
||||||
|
CREATE INDEX idx_orders_user ON orders(user_id);
|
||||||
|
|
||||||
|
**Задача:**
|
||||||
|
|
||||||
|
- объяснить, зачем нужен первый;
|
||||||
|
ЧТОБЫ ОДНОВРЕМЕННО ИСКАТЬ ПОЛЬЗОВАТЕЛЕЙ В СОВОКУПНОСТИ С ДАТОЙ СОЗДАНИЯ. И ТАКЖЕ СОРТИРОВАТЬ ПО ДАТЕ СОЗДАНИЯ ПОЛЬЗОВАТЛЕЙ .
|
||||||
|
|
||||||
|
- нужен ли второй или его можно удалить;
|
||||||
|
ВТОРОЙ НЕ НУЖЕН, ПОТОУ ЧТО ПЕРВЫЙ МОЖЕТ РАБОТАТЬ ПО ЛЕВОМУ ПРЕФИКСУ. ВТОРОЙ ИНДЕКС ЛИШЬ ЗАНИМАЕТ ЛИШНЕЕ МЕСТО.
|
||||||
Reference in New Issue
Block a user