Чувствительность к регистру при запросе SQL Server 2005 из .NET с использованием OleDB

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

Вопрос

У меня есть запрос, который я выполняю из приложения .NET к базе данных SQL Server, и, похоже, его выполнение занимает довольно много времени (более 5 минут).Я создал тестовое приложение на c #, чтобы попытаться увидеть, о чем так долго говорили (запрос должен вернуться быстро).

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

Кто-нибудь видел это раньше?Мне интересно, отключены ли какие-либо службы на нашем сервере (поскольку у коллеги такая же проблема) или на наших компьютерах.

Заранее спасибо за любую помощь в этом.

Пример кода ниже (Разница в первой строке запроса в конце (fk_source vs.fk _ источник):

//Original
    OleDbCommand comm = new OleDbCommand("select min(ctc.serial_no) as MIN_INTERVAL from countstypecode ctc, source s, countstype ct, counts c where ct.value_id=c.value_id and s.c_id=ct.fk_source and " +
      "ct.timeinterval=ctc.typename and ct.timeinterval in ('15min','1h','1day') and c.time_stamp >=  CONVERT(datetime,'01-01-2008',105)  and c.time_stamp < " +
      "CONVERT(datetime,'01-01-2009',105)  and s.c_id = '27038dbb19ed93db011a315297df3b7a'", dbConn);

//Rebuilt
    OleDbCommand comm = new OleDbCommand("select min(ctc.serial_no) as MIN_INTERVAL from countstypecode ctc, source s, countstype ct, counts c where ct.value_id=c.value_id and s.c_id=ct.fk_Source and " +
      "ct.timeinterval=ctc.typename and ct.timeinterval in ('15min','1h','1day') and c.time_stamp >= CONVERT(datetime,'01-01-2008',105) and c.time_stamp < " +
      "CONVERT(datetime,'01-01-2009',105) and s.c_id='27038dbb19ed93db011a315297df3b7a'", dbConn);
Это было полезно?

Решение

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

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

Попробуй это....

Подключитесь к SQL Server Management Studio.

DBCC MemoryStatus

Select Columns... From TABLES.... Where....

dbcc MemoryStatus

Select Columns... From tables.... Where....

dbcc MemoryStatus

Я думаю, вы обнаружите, что TotalProcs изменяется при изменении оператора (даже если единственное изменение чувствительно к регистру).

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

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

Поскольку вы используете SQL Server 2005, пробовали ли вы использовать объект SqlCommand вместо объекта OleDbCommand?

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

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

во-первых, вы на 100% уверены, что именно запрос идет не так?Проверьте профиль трассировки в sql server, чтобы узнать, сколько времени он занимает в базе данных.

Во-вторых, получаете ли вы обратно такое же количество результатов?Заглавная буква не должна иметь значения по умолчанию в sql server, но ее можно было бы настроить по-другому.

Если бы у меня был запрос, который занял "5 + минут", я бы не беспокоился о 100 миллисекундах, которые требуются для сопоставления регистра строки.

спасибо за все ваши ответы, я отвечу на каждый по очереди:

1) Расс, я согласен, что SqlConnection было бы лучше, но, к сожалению, я не могу установить тип соединения.Я только что создал небольшое приложение для тестирования этого запроса, но запрос динамически создается в гораздо большем приложении.

2) gbjbaanb, я думаю, это не проблема сервера, потому что я могу запустить оба запроса из management studio примерно за одно и то же время, это кажется проблемой только при запуске через oledb в .net (1.1 и 2.0).Мы запустили профилировщик, и файл трассировки подтвердил, что выполнение запроса при вызове таким образом заняло более 5 минут.

3) Джоэл Коэхорн, Согласен, но на самом деле я пытаюсь понять, почему, потому что прямо сейчас мы не знаем, насколько велика эта проблема и в чем она заключается.

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

Спасибо G Mastros за наиболее полный ответ, хотя, оглядываясь назад, обновление статистики было предложено Кейдом.Однако решение G Mastos лучше соответствовало моему уровню владения SQL Server.

Спасибо, что помогли всем!

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

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