`value` UInt32, `id` UInt32, `ts` DateTime
)
ENGINE = MergeTree
PARTITION BY toYYYYMM(ts)
ORDER BY tuple();
Добавляю индекс:
ALTER TABLE skip_idx ADD INDEX test_idx `value` TYPE minmax GRANULARITY 1;
ALTER TABLE skip_idx MATERIALIZE INDEX test_idx;
Заполняю данными:
INSERT INTO skip_idx SELECT
rand(), number, now() + intDiv(number, 10)
FROM numbers(1000000000);
Делаю поиск по ключу value:
SELECT count() FROM skip_idx WHERE value = 214678225
Результат:
1 rows in set. Elapsed: 0.191 sec. Processed 1.00 billion rows, 4.00 GB (5.25 billion rows/s., 20.99 GB/s.)
Почему при имеющемся индексе, выполняется просмотр всех данных таблицы?
А также почему при гранулярности 1, выполняется просмотр всех гранул, а не остановка после первого вхождения, ведь дальше должны идти значения заведомо больше искомого:
Expression ((Projection + Before ORDER BY)) │
│ Aggregating │
│ Expression (Before GROUP BY) │
│ Filter (WHERE) │
│ SettingQuotaAndLimits │
│ ReadFromMergeTree │
│ Indexes: │
│ MinMax │
│ Condition: true │
│ Parts: 232/232 │
│ Granules: 122097/122097 │
│ Partition │
│ Condition: true │
│ Parts: 232/232 │
│ Granules: 122097/122097 │
│ Skip │
│ Name: id_idx │
│ Description: minmax GRANULARITY 1 │
│ Parts: 232/232 │
│ Granules: 122097/122097 │
>А также почему при гранулярности 1, выполняется просмотр всех гранул, а не остановка после первого вхождения, ведь дальше должны идти значения заведомо больше искомого Там нет никакой последовательности. Данные у вас никак не отсортированы. Гранулы идут в случайном порядке, поэтому нужно проверять minmax для всех.
Так во время построения индекса это условие и должно проверяться и сохраняться в индексе. А после, при поиске значения в индексе и его обнаружении, брать из него положение этих данных, например номер куска и смещение в нем, и читать. Или как-то иначе?
Нет, он про то что вроде каждой грануле было сказано, какое максимальное, а какое минимальное число, в ней и они должны быть отсечены
При построении индекса minmax должен формироваться упорядоченный список значений колонок по которым этот индекс строится. Соответственно, если делать запрос с использованием этого индекса на равенство, то при совпадении, даже если просто просматривать весь индекс, поиск должен заканчиваться при первом большем, чем запрошенное, значении. Этого не происходит в примере, что я скинул.
Нет. В этом ваше заблуждение, идущее корнями к индексам постгреса. Тут не так, мы про это сказали уже не раз. Попробуйте от него отказаться.
Так вот я и пытаюсь понять фундаментальные отличия, на которые можно будет опираться при планировании индексов. Но так и или иначе, любой индекс должен на что-то ссылаться. На что ссылается индекс пропуска, как он адресует искомые данные?
https://clickhouse.com/docs/ru/engines/table-engines/mergetree-family/mergetree/
Записи индекса пропуска ни на что не ссылаются. В них есть информация, которую можно проверить и принять решение о пропуске набора гранул.
Обсуждают сегодня