Огромная таблица в базе данных SQL 2005 требует большей производительности!

StackOverflow https://stackoverflow.com/questions/2219624

Вопрос

Я работаю над веб-приложением, управляемым данными, которое использует базу данных SQL 2005 (стандартная версия).

Одна из таблиц довольно большая (более 8 миллионов строк и около 30 столбцов).Размер таблицы, очевидно, влияет на производительность веб-сайта, который выбирает элементы из таблицы через сохраненные процедуры.Таблица проиндексирована, но производительность по-прежнему низкая из-за огромного количества строк в таблице — это часть проблемы — таблица одинаково читается и обновляется, поэтому мы не можем добавлять/удалять индексы, не создавая один из них. операции хуже.

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

Мы знаем о таких вещах, как распределенные секционированные представления, но для всех этих функций требуется Enterprise Edition, которую клиент не будет покупать (и нет, бросать в нее оборудование тоже не получится).

Это было полезно?

Решение

Вы всегда можете создать собственное «разделение для бедняков / DPV», даже если это не похоже на правильный способ сделать это.Это всего лишь широкий концептуальный подход:

  1. Создайте новую таблицу для данных текущего года — та же структура, те же индексы.Настройте хранимую процедуру, которая записывает данные в основную большую таблицу, для записи в обе таблицы (только временно).Я рекомендую сделать логику хранимой процедуры такой: IF CURRENT_TIMESTAMP >= '[некоторая целая дата без времени]' - это облегчит обратное заполнение данных в этой таблице, которые предшествуют изменению процедуры, которая начинает там регистрироваться.

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

  3. Получив копию всей таблицы, вы можете создать представления, ссылающиеся только на текущий год, другое представление, ссылающееся на текущий год с 2005 по 2005 год (используя UNION ALL между текущей таблицей и таблицами в другой базе данных, которые >= 2005). ), а другой ссылается на все три набора таблиц (упомянутые и таблицы, выпущенные до 2005 года).Конечно, вы можете разбить это еще больше, но я просто хотел сохранить концепцию минимальной.

  4. Измените свои хранимые процедуры, которые читают данные, чтобы они были «умнее» — если запрошенный диапазон дат попадает в текущий календарный год, используйте наименьшее представление, которое является только локальным;если диапазон дат >= 2005 г., используйте второе представление, в противном случае используйте третье представление.Вы можете следовать аналогичной логике с хранимыми процедурами записи, если вы делаете больше, чем просто вставляете новые данные, относящиеся только к текущему году.

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

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

Другие советы

производительность низкая из-за большого количества строк в таблице

8 миллионов строк — это не так уж и безумно.Вы проверяли свои планы запросов?

таблица одинаково читается и обновляется

Вы на самом деле обновляете индексированный столбец или он одинаково читается и вставлен к?

(и нет, бросать в него оборудование тоже не получится)

Это очень жаль, потому что оперативная память очень дешева.

Перестройте все свои индексы.Это повысит производительность запросов.Как это сделать этот и еще о влиянии на перестроение кластеризованного и некластеризованного индекса. здесь

Во-вторых, выполните дефрагментацию на диске, на котором хранится БД.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top