Когда лучше создавать STATISTICS, а не создавать Index?

38

Я нашел много информации о том, что STATISTICS : как они поддерживаются, как их можно создавать вручную или автоматически из запросов или индексов и так далее. Но я не смог найти каких-либо указаний или информации о «наилучших методах» в отношении того, когдадля их создания: какие ситуации выигрывают больше от созданного вручную объекта STATISTICS, чем от Index. Я видел созданные вручную отфильтрованные статистические данные, помогающие выполнять запросы к многораздельным таблицам (потому что статистика, созданная для индексов, охватывает всю таблицу, а не для каждого раздела - отличная информация!), Но, безусловно, должны существовать другие сценарии, которые выиграли бы от объекта статистики, пока не нуждаются в детализации индекса и не стоят затрат на его обслуживание или увеличение шансов на блокировку / взаимоблокировку.

@JonathanFite в комментарии упомянул различие между индексами и статистикой:

Индексы помогут SQL быстрее находить данные, создавая запросы, которые сортируются не так, как сама таблица. Статистика помогает SQL определить, сколько памяти / усилий потребуется для выполнения запроса.

Это отличная информация, в основном потому, что она помогает мне уточнить мой вопрос:

Как знание этого (или любая другая техническая информация на то , что S и как ы , связанное с поведением и характером STATISTICS) поможет определить , когда выбрать CREATE STATISTICSболее CREATE INDEX, особенно при создании индекса будет создать соответствующий STATISTICSобъект? Какой сценарий будет лучше обслуживать, имея только информацию STATISTICS и не имея индекса?

Было бы очень полезно, если это возможно, иметь рабочий пример сценария, в котором STATISTICSобъект лучше подходит, чем объект INDEX.


Так как я визуальный ученик / мыслитель, я подумал, что это может помочь увидеть различия между ними STATISTICSи INDEXрядом, как возможное средство, помогающее определить, когда STATISTICSлучший выбор.

Thingy           PROs                             CONs
-------          ----------                       -------------------
INDEX            * Can help sorts.                * Takes up space.
                 * Contains data (can             * Needs to be maintained (extra I/O).
                   "cover" a query).              * More chances for blocking / dead-locks.

STATISTICS       * Takes up very little space.    * Cannot help sorts.
                 * Lighter maintenance / won't    * Cannot "cover" queries.
                   slow down DML operations.
                 * Does not increase chances
                   of blocking / dead-locks.

Ниже приведены некоторые ресурсы, которые я нашел во время поиска этого, тот, который даже задает тот же вопрос, но на него не было ответа:

Индекс SQL Server против статистики

Вопросы статистики SQL Server, которые мы стеснялись задавать

Статистика. Возможны ли многоколонные гистограммы?

** Чтобы быть ясным, у меня нет ответа на этот вопрос, и я на самом деле хочу получить обратную связь от, надеюсь, нескольких человек, чтобы предоставить то, что, как ни странно, отсутствует информация здесь, в сети.

Соломон Руцкий
источник
1
Индексы помогут SQL быстрее находить данные, создавая запросы, которые сортируются не так, как сама таблица. Статистика помогает SQL определить, сколько памяти / усилий потребуется для выполнения запроса.
Джонатан Файт
@JonathanFite Спасибо за этот комментарий. Я включил это в свой вопрос :).
Соломон Руцкий,
После комментария @ JonathanFite может показаться, что статистика лучше всего подходит для повышения производительности специальных систем / таблиц / шаблонов запросов, а индексы - для предсказуемых шаблонов запросов. Я имею в виду это скорее вопрос, чем утверждение.
Дейв

Ответы:

19

Ваш вопрос вращается вокруг - Когда это хорошая вещь, чтобы просто создать статистику против создания индекса (который создает статистику).

Из моих замечаний по внутренним компонентам сервера sql (класс SQLSkills - IE1 и IE2) и книги по внутренним компонентам SQL Server ниже мое ограниченное понимание:

Статистика SQL Server - это не что иное, как системные объекты, которые содержат важную информацию о значениях ключей индекса и обычных значениях столбцов.

SQL Server использует модель, основанную на затратах, чтобы выбрать «достаточно хороший» план выполнения как можно быстрее. Оценка количества элементов (оценка количества строк, подлежащих обработке на каждом этапе выполнения запроса) является наиболее важным фактором в оптимизации запроса, который влияет на стратегию соединения, требование предоставления памяти, выбор рабочего потока, а также выбор индексов при доступе к данным. ,

SQL Server не будет использовать некластеризованные индексы, когда он оценивает, что большое нет. операций KEY или RID потребуется, поэтому он ведет статистику по индексам (и по столбцам), что поможет в таких оценках.

Есть две важные вещи о статистике:

  1. Гистограмма хранит информацию о распределении данных ТОЛЬКО для самого левого столбца статистики (индекса). Он также хранит информацию о плотности столбцов ключевых значений. По сути, гистограмма хранит распределение данных только для самого левого столбца статистики.

  2. SQL Server сохранит не более 200 шагов в гистограмме независимо от размера таблицы. Интервалы, охватываемые каждым шагом гистограммы, увеличиваются с ростом таблицы, что приводит к «менее точной» статистике для больших таблиц.

    Помните, что селективность индекса - это показатель, который обратно пропорционален плотности, т. Е. Чем больше уникальных значений в столбце, тем выше его селективность.

Когда отдельные запросы выполняются не очень часто, вы можете выбрать создание статистики на уровне столбца, а не индекса. Статистика на уровне столбцов помогает оптимизатору запросов находить лучшие планы выполнения, даже если эти планы выполнения неоптимальны из-за включенного сканирования индекса. В то же время статистика не добавляет накладных расходов во время операций по изменению данных и помогает избежать обслуживания индекса. Этот подход работает только для редко выполняемых запросов.

См .:

Примечание: кто-то, например Пол Уайт или Аарон Бертран, может принять участие, чтобы придать больше цвета вашему хорошему вопросу .

Кин Шах
источник
«SQL Server не будет использовать некластеризованные индексы, когда он оценивает, что потребуется большое количество операций цикла KEY или RID». Итак, может ли QO использовать объект статистики, основанный на индексе, независимо от индекса? Это означает, что если индекс не является оптимальным, но в запросе находится ведущий столбец, тогда статистика по-прежнему актуальна. Так будут ли они использоваться? Или эта информация подразумевает, что могут быть случаи, когда индекс вряд ли будет использоваться, но поскольку статистика все еще имеет значение, то нет реальной причины для создания индекса, просто сделайте статистику?
Соломон Руцкий
8

Я бы сказал, что вам нужен индекс, когда вы должны иметь возможность ограничить объем данных / быстро получить правильные данные на основе полей.

Вам нужна статистика, когда вам нужен оптимизатор, чтобы понять природу данных, чтобы иметь возможность выполнять операции наилучшим образом.

Как я понял, отфильтрованная статистика помогает, когда у вас есть перекосы в данных, которые сильно влияют на план, например, при переполнении стека, у немногих пользователей огромное количество постов, поэтому использование только среднего количества постов на пользователя не является наилучшей оценкой. Таким образом, вы можете создать отфильтрованную статистику по userId на основе имени пользователя, и тогда SQL Server должен знать, что когда это имя пользователя находится в запросе, это будет идентификатором пользователя, который он получит, и он должен быть в состоянии выяснить, что Индексированное поле в таблице постов будет содержать огромное количество строк с таким идентификатором, потому что там существует гистограмма. Со средними это невозможно сделать.

Джеймс З
источник
1
Привет, и спасибо за ответ. Итак, когда мне нужно / нужно, чтобы оптимизатор лучше понимал природу данных, и при этом не ограничивал эти данные или не хотел быстрее их получать, или мне нужно было бы «покрывать» запрос? То же самое для вашего примера фильтрованного индекса. Я понимаю, что вы говорите в плане исключения краевых случаев из средних значений, но почему фильтрованная статистика лучше, чем фильтрованный индекс по тем же полям? Это различие, к которому я пытаюсь добраться.
Соломон Руцки
Как и в примере, вы не можете создать отфильтрованный индекс по имени пользователя для таблицы сообщений, потому что он там не существует. Вы можете создать его на основе идентификатора пользователя, но этого нет в предложении where.
Джеймс З,
Но не UserIDбудет в состоянии JOIN, даже если не в WHERE? И разве этого не достаточно, чтобы подобрать отфильтрованный индекс?
Соломон Руцкий,
@srutzky Возможно, более вероятно в самых последних версиях, но в целом я бы не стал полагаться на это ... в большинстве случаев предикаты должны точно совпадать. Я забыл, если бы они исправили это, но в какой-то момент отфильтрованный индекс WHERE BitColumn = 0не был бы выбран для простого запроса WHERE BitColumn <> 1. (И чтобы быть ясным, битовый столбец не может быть обнуляемым.) Я думаю, что были похожие случаи, такие как IntColumn > 10несоответствие IntColumn >= 11.
Аарон Бертран
Отфильтрованные индексы нельзя использовать, если есть вероятность, что в следующий раз, когда кто-то использует планы, отфильтрованный индекс больше не подходит. Я не могу думать ни о каких объединениях, которые могли бы использовать фильтрованный индекс. Даже переменные нельзя использовать, потому что в следующий раз значение может быть чем-то неподходящим.
Джеймс З,
4

От 70-461 Учебная книга Ицик Бен-Ган

Есть только несколько возможных причин для создания статистики вручную. Одним примером является случай, когда предикат запроса содержит несколько столбцов, которые имеют связи между столбцами; статистика по нескольким столбцам может помочь улучшить план запроса. Статистика по нескольким столбцам содержит плотности между столбцами, которые недоступны в статистике по одному столбцу. Однако, если столбцы уже находятся в одном индексе, многоколоночный объект статистики уже существует, поэтому не следует создавать дополнительный вручную.

Кентаро
источник
Спасибо за публикацию этого. Это отвечает на часть моего вопроса, но все еще оставляет открытым вопрос: если мне нужна многостолбцовая статистика, зачем мне создавать только СТАТИСТИКУ вместо Индекса, которая будет включать СТАТИСТИКУ плюс дополнительную информацию, которая могла бы дополнительно помочь запросу ( х годов)?
Соломон Руцкий,
1
Я думаю, что объяснение Кина будет дальше объяснять, что вы ищете. Возможно куча, которая часто вставляется, но редко запрашивается?
Кентаро