Кластерный и некластерный первичный ключ
begin transaction;
create table person_id(person_id integer primary key);
insert into person_id values(1);
... snip ...
insert into person_id values(50000);
commit;
Этот код занимает около 0,9 секунд на моем компьютере и создает файл БД, занимающий 392 КБ. Эти цифры становятся 1,4 секунды и 864K, если я изменю вторую строку на
create table person_id(person_id integer nonclustered primary key);
Почему это так?
4 ответа
Отличный ответ на этот вопрос доступен на сайте DBA StackExchange: https://dba.stackexchange.com/questions/7741/when-should-a-primary-key-be-declared-non-clustered/7744
Кластеризация первичного ключа сохраняет его со строками; это означает, что он занимает меньше места (так как нет отдельных блоков индекса). Однако, как правило, его основное преимущество заключается в том, что при сканировании диапазона можно получить доступ к строкам, которые находятся в одном блоке, что сокращает операции ввода-вывода, что становится довольно важным, когда у вас большой набор данных (не 50 тыс. Дюймов).
Я думаю, что 50 тыс. Дюймов - это довольно искусственный тест, а не тот, который вас волнует в реальном мире.
[Только как идея]
Возможно, когда вы явно указываете, что в качестве кластеризованного ключа должны быть взяты целочисленные столбцы, он делает именно это. Но когда вы говорите ему не использовать ваш целочисленный столбец, он все равно создает закулисный индекс, но выбирает другой тип данных для этого, предположим, в два раза больше. Затем каждая из этих записей должна ссылаться на записи в таблице, и вот, пожалуйста, размер увеличивается.
Я рандомизировал операторы вставки и повторил запрос со значениями от одного до полумиллиона. Интересно, что и кластеризованные, и некластеризованные файлы БД теперь занимают точное количество места (вплоть до байта). Однако вставки в кластеризованную базу данных все еще быстрее.
Для меня это противоречит интуиции. Когда я сообщаю кластеру базы данных эти значения - я говорю базе данных... эти значения должны быть в таком порядке, когда я вернусь, чтобы получить их. Когда у меня нет спецификации, я, по сути, говорю БД - посмотрите, возьмите эти значения и расположите их так, как вам нравится - все, что облегчает вашу жизнь.
Теоретически, эта дополнительная свобода никогда не должна замедлять запросы. Возможно, не ускорять их все время, но никогда не замедлять. Мысли?