Важной частью здесь является наличие соответствующего индекса .Вы можете попробовать эту небольшую настройку теста:
Создать схему x
для тестирования:
-- DROP SCHEMA x CASCADE; -- to wipe it all for a retest or when done.
CREATE SCHEMA x;
CREATE TABLE x.tbl(id serial, name text);
Вставить 10000 случайных строк:
INSERT INTO x.tbl(name) SELECT 'x' || generate_series(1,10000);
Вставить еще 10000 строк с помощьюповторяющиеся имена:
INSERT INTO x.tbl(name) SELECT 'y' || generate_series(1,10000)%20;
Удалите случайные 10%, чтобы сделать его более реальным:
DELETE FROM x.tbl WHERE random() < 0.1;
ANALYZE x.tbl;
Запрос может выглядеть следующим образом:
SELECT *
FROM x.tbl
WHERE name = 'y17'
ORDER BY id DESC
LIMIT 1;
->Общее время выполнения: 5,535 мс
CREATE INDEX tbl_name_idx on x.tbl(name);
-> Общее время выполнения: 1,228 мс
DROP INDEX x.tbl_name_idx;
CREATE INDEX tbl_name_id_idx on x.tbl(name, id);
-> Общее время выполнения: 0,053 мс
DROP INDEX x.tbl_name_id_idx;
CREATE INDEX tbl_name_id_idx on x.tbl(name, id DESC);
-> Общее время выполнения: 0,048 мс
DROP INDEX x.tbl_name_id_idx;
CREATE INDEX tbl_name_idx on x.tbl(name);
CLUSTER x.tbl using tbl_name_idx;
-> Общее время выполнения: 1,144 мс
DROP INDEX x.tbl_name_id_idx;
CREATE INDEX tbl_name_id_idx on x.tbl(name, id DESC);
CLUSTER x.tbl using tbl_name_id_idx;
-> Общее время выполнения: 0,047 мс
Заключение
С индексом подбора запрос выполняется на более чем в 100 раз быстрее .
Самым эффективным является многостолбцовый индекс с первым столбцом фильтра и последним столбцом сортировки.
Соответствие сортировкапорядок в индексе немного помогает в этом случае.
Кластеризация помогает с простым индексом, потому что все еще многие столбцы должны быть прочитаны из таблицы, и тИх можно найти в соседних блоках после кластеризации.В этом случае это не поможет с многоколоночным индексом, потому что из таблицы нужно извлечь только одну запись.
Подробнее о многоколоночных индексах в руководстве .
Всеиз этих эффектов растут с размером таблицы.10000 строк двух крошечных столбцов - это очень маленький тестовый пример.