Предварительно загрузить данные результатов SQL-запроса в кеш - PullRequest
1 голос
/ 23 апреля 2010

У меня следующая ситуация:

  • .net 3.5 Клиентское приложение WinForm, обращающееся к SQL Server 2008
  • Некоторые запросы, возвращающие относительно большой объем данных, довольно часто используются формой
  • Пользователи используют локальный SQL Express и перезагружают свои компьютеры хотя бы ежедневно
  • Другие пользователи работают удаленно через медленные сетевые подключения

Проблема заключается в том, что после перезагрузкив первый раз, когда пользователи открывают эту форму, запросы выполняются очень медленно и на быстром компьютере выполняются более или менее 15 секунд.После этого те же запросы занимают всего 3 секунды.Конечно, это связано с тем, что данные не кэшируются и должны быть сначала загружены с диска.

Мой вопрос:
Можно ли заранее принудительно загрузить необходимые данные в кэш SQL Server?

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

У вас есть какая-нибудь другая идея?

Ответы [ 4 ]

3 голосов
/ 23 апреля 2010

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

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

1 голос
/ 23 апреля 2010

Я не уверен, как вы выполняете свои запросы, но вы могли бы сделать:

SqlCommand Command = /* your command */
Command.ExecuteReader(CommandBehavior.SchemaOnly).Dispose();

Выполнение вашей команды с использованием только команды схемы добавит SET FMTONLY ON к запросу и вызовет SQLСервер для получения метаданных о наборе результатов (требуется генерация плана), но фактически не выполнит команду .

0 голосов
/ 18 мая 2010

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

Спасибо всем вам за ваш действительнобыстрая помощь по этому вопросу!

0 голосов
/ 23 апреля 2010

Чтобы сузить источник проблемы, вы всегда можете использовать объекты SQL Server в perfmon, чтобы получить общее представление о том, как работает локальный экземпляр SQL Server Express.

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

Также вы можете проверить http://msdn.microsoft.com/en-us/library/ms191129.aspx В нем описывается, как настроить автоматический запуск sproc при запуске службы SQL Server. Если вы извлекаете данные, которые вам нужны, с помощью этого элемента, то, возможно, данные останутся в кэше и улучшат производительность при первом получении данных конечным пользователем через вашу форму.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...