Это плохая стратегия индексации для таблицы? - PullRequest
0 голосов
/ 15 февраля 2009

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

Metadata 
ResultID (PK, int, not null) 
MappedFieldname (char(50), not null) 
Fieldname (PK, char(50), not null) 
Fieldvalue (text, null)

Существует кластеризованный индекс по ResultID и Fieldname. Эта таблица обычно содержит миллионы строк (в одном случае она содержит 500 миллионов). Таблица заполняется 24 рабочими, работающими по 4 потока в каждом, когда данные обрабатываются. Это приводит ко многим непоследовательным вставкам. Позже, после обработки, некоторые данные добавляются в эту таблицу некоторыми нашими собственными программами. Фрагментация для данной таблицы составляет не менее 50%. В случае самой большой таблицы это на 90%. У нас нет DBA. Я знаю, что нам крайне необходима стратегия обслуживания БД. Насколько я знаю, я студент колледжа, работаю неполный рабочий день в этой компании.

У меня такой вопрос, является ли кластерный индекс лучшим способом для этого? Следует ли учитывать другой индекс? Есть ли хорошие ссылки для этого типа и аналогичных специальных задач DBA?

Ответы [ 4 ]

4 голосов
/ 15 февраля 2009

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

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

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

Определите типичный запрос к таблице и разместите индексы соответственно. Чем больше у вас индексов, тем медленнее будут изменяться данные (INSERT / UPDATEs / DELETEs). Не создавайте слишком много индексов, например для полей, которые вряд ли будут отфильтрованы / отсортированы.

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

1 голос
/ 16 февраля 2009

Внимательно изучите ваши запросы - те, которые попадают в таблицу данных. Будет ли индекс служить? Если у вас есть индекс в (ResultID, FieldName) в этом порядке, но вы запрашиваете возможные значения ResultID для данного имени поля, вполне вероятно, что СУБД будет игнорировать индекс. Напротив, если у вас есть индекс (FieldName, ResultID), он, вероятно, будет использовать этот индекс - конечно, для простых поисков значений (WHERE FieldName = 'abc'). С точки зрения уникальности любой индекс работает хорошо; с точки зрения оптимизации запросов существует (по крайней мере, потенциально) огромная разница.

Используйте EXPLAIN , чтобы увидеть, как ваши запросы обрабатываются вашей СУБД.

Кластеризованная или некластерная индексация обычно является эффектом оптимизации второго порядка в СУБД. Если у вас правильный индекс, есть небольшая разница между кластеризованным и некластеризованным индексом (с большим штрафом за обновление кластеризованного индекса в качестве компенсации за немного меньшее время выбора). Прежде чем беспокоиться об эффектах второго порядка, убедитесь, что все остальное оптимизировано.

0 голосов
/ 16 февраля 2009

Я знаю, что нам крайне необходима стратегия обслуживания БД.

+ 1 для определения, что нужно

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

Продолжай учиться, набирайся опыта, а пока найди опытного консультанта.

Таблица заполнена 24 рабочими, работающими по 4 потока в каждом

Полагаю, это довольно важно для работы в течение рабочего дня, а простои - плохая новость? Если это так, не стоит с этим связываться.

Существует кластеризованный индекс для ResultID и Fieldname

Является ли ResultID первым столбцом в PK, как вы указываете?

Если так, то я держу пари, что он недостаточно избирателен и, в зависимости от потребностей запросов, порядок полей PK следует менять местами (несмотря на то, что этот составной ключ выглядит плохим выбором для кластеризованного PK)

Каков результат:

ВЫБРАТЬ СЧЕТЧИК (*), СЧЕТЧИК (ОТЛИЧИТЕЛЬНЫЙ ResultID) ОТ MyTable

Если первое число, скажем, в 4 раза больше, чем второе, или больше, вы, скорее всего, будете получать сканы в предпочтении к поиску из-за низкой избирательности ResultsID, а некоторые простые изменения приведут к огромной производительности улучшения.

Кроме того, имя поля довольно широкое (50 символов), поэтому к любым вторичным индексам будет добавлено 50 + 4 байта к каждой записи индекса. Поля действительно CHAR, а не VARCHAR?

Лично я бы рассмотрел увеличение плотности листовых страниц. На 90% вы оставите только несколько пробелов - возможно, один на страницу. Но при большой таблице из 500 миллионов строк более высокая плотность упаковки может означать меньшее количество уровней в дереве и, следовательно, меньше запросов на поиск. Напротив, почти каждая вставка для данной страницы потребует разбиения страницы. Это предпочло бы вставки, которые кластеризованы, поэтому могут не подходить (учитывая, что ваши данные вставки, вероятно, не кластеризованы). Как и во многих других случаях, вам необходимо выполнить тест, чтобы определить, какая плотность ключей индекса работает лучше всего. В SQL Server есть инструменты, помогающие проанализировать, как анализируются запросы, кэшируются ли они, сколько сканирований вызываемой ими таблицы, какие запросы выполняются «медленно» и т. Д.

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

Вам действительно ДЕЙСТВИТЕЛЬНО нужно тщательно продумать правила обслуживания таблиц, содержащих 500 миллионов строк и ежедневно загружаемых вставок. Извините, но я испытываю огромное разочарование по поводу компаний, попавших в это состояние.

Таблица нуждается в дефрагментации (если у вас нет кластеризованного индекса, вариантов станет меньше, поэтому сохраняйте их, пока не решите, что есть лучший кандидат). «Онлайн» методы дефрагментации будут иметь скромное влияние на производительность и могут пускаться в пух и прах - и их можно будет безопасно прервать, если они превысят ограничения времени / ЦП [хотя это, скорее всего, потребует некоторого программирования]. Если у вас есть «тихий» слот, используйте его для дефрагментации таблиц и обновления статистики по индексам. Не ждите до выходных, чтобы попытаться сделать все столы за один раз - делайте как можно больше / больше в любое тихое время суток (предположительно ночью).

Дефрагментация таблиц может привести к значительному увеличению использования журнала транзакций, поэтому убедитесь, что резервные копии любых TLog-файлов выполняются часто (у нас есть 10-минутная политика резервного копирования TLog, которую мы увеличиваем до каждой минуты во время дефрагментации таблицы, чтобы процесс дефрагментации не становится определением необходимого пространства Tlog!)

0 голосов
/ 15 февраля 2009

Насколько я вижу, кластерный индекс в порядке. Что касается других индексов, вам нужно будет предоставить типичные запросы SQL, которые работают с этой таблицей. Просто создание индекса на пустом месте никогда не является хорошей идеей. Вы говорите о фрагментации и индексации, означает ли это, что вы подозреваете, что выполнение запроса замедляется? Или вы просто хотите сжать / дефрагментировать базу данных / индекс?

Хорошей идеей является задача время от времени дефрагментировать индексы в нерабочее время, хотя следует учитывать, что при частых / случайных вставках не мешает иметь некоторое свободное место в таблице, чтобы предотвратить появление разбивает (что влияет на производительность).

...