Производительность запросов SQL Server в более длинном диапазоне дат - PullRequest
3 голосов
/ 13 сентября 2011

Я пытаюсь запросить таблицу, в которой есть столбец, в котором хранятся данные транзакции в формате XML. Моя опция filer - это фактически 1 узел в моих данных XML. Так что ниже мой запрос

SELECT eRefNo, eCreationDate, eData 
FROM TableA
WHERE CAST(CAST(CAST(eData AS text) AS xml ).query('Test/Header/ExportToGMACS/text()')AS nvarchar(1000)) = 'True' 
AND ((CAST(CAST(CAST(eData AS text) AS xml ).query('Test/PaymentAccountingDetail/PaymentAccounting1/KindOfPayment[@MPText]')AS nvarchar(1000)) = 'Claims') 
OR (CONVERT(datetime, CAST(CAST(CAST(eData AS text) AS xml ).query('Test/PaymentAccountingDetail/PaymentAccounting1/PaymentDate/text()')AS nvarchar(1000)), 103) >= convert(datetime, '01/01/2011', 103) AND (CONVERT(datetime, CAST(CAST(CAST(eData AS text) AS xml ).query('Test/PaymentAccountingDetail/PaymentAccounting1/PaymentDate/text()')AS nvarchar(1000)), 103) <= convert(datetime, '31/07/2011', 103))) 
OR (CONVERT(datetime, CAST(CAST(CAST(eData AS text) AS xml ).query('Test/PaymentAccountingDetail/PaymentAccounting2/PaymentDate/text()')AS nvarchar(1000)), 103) >= convert(datetime, '01/01/2011', 103) AND (CONVERT(datetime, CAST(CAST(CAST(eData AS text) AS xml ).query('Test/PaymentAccountingDetail/PaymentAccounting2/PaymentDate/text()')AS nvarchar(1000)), 103) <= convert(datetime, '31/07/2011', 103))) 
OR (CONVERT(datetime, CAST(CAST(CAST(eData AS text) AS xml ).query('Test/PaymentAccountingDetail/PaymentAccounting3/PaymentDate/text()')AS nvarchar(1000)), 103) >= convert(datetime, '01/01/2011', 103) AND (CONVERT(datetime, CAST(CAST(CAST(eData AS text) AS xml ).query('Test/PaymentAccountingDetail/PaymentAccounting3/PaymentDate/text()')AS nvarchar(1000)), 103) <= convert(datetime, '31/07/2011', 103))) 
OR (CONVERT(datetime, CAST(CAST(CAST(eData AS text) AS xml ).query('Test/PaymentAccountingDetail/PaymentAccounting4/PaymentDate/text()')AS nvarchar(1000)), 103) >= convert(datetime, '01/01/2011', 103) AND (CONVERT(datetime, CAST(CAST(CAST(eData AS text) AS xml ).query('Test/PaymentAccountingDetail/PaymentAccounting4/PaymentDate/text()')AS nvarchar(1000)), 103) <= convert(datetime, '31/07/2011', 103))) 
OR (CONVERT(datetime, CAST(CAST(CAST(eData AS text) AS xml ).query('Test/PaymentAccountingDetail/PaymentAccounting5/PaymentDate/text()')AS nvarchar(1000)), 103) >= convert(datetime, '01/01/2011', 103) AND (CONVERT(datetime, CAST(CAST(CAST(eData AS text) AS xml ).query('Test/PaymentAccountingDetail/PaymentAccounting5/PaymentDate/text()')AS nvarchar(1000)), 103) <= convert(datetime, '31/07/2011', 103))) 
OR (CONVERT(datetime, CAST(CAST(CAST(eData AS text) AS xml ).query('Test/PaymentAccountingDetail/PaymentAccounting6/PaymentDate/text()')AS nvarchar(1000)), 103) >= convert(datetime, '01/01/2011', 103) AND (CONVERT(datetime, CAST(CAST(CAST(eData AS text) AS xml ).query('Test/PaymentAccountingDetail/PaymentAccounting6/PaymentDate/text()')AS nvarchar(1000)), 103) <= convert(datetime, '31/07/2011', 103)))) 

Когда я устанавливаю свой диапазон дат для поиска от 01/Jan/2011 до 31/Jul/2011, это занимает БЫСТРОЕ по сравнению с тем, когда мой диапазон дат составляет от 01/Jul/2011 до 31/Jul/2011.

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

Любые эксперты, пожалуйста, сообщите.

Спасибо Johnson


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

Мой главный вопрос: фильтр с более широким диапазоном дат занимает меньше времени, чем фильтр с более коротким диапазоном дат.

Есть идеи, в чем причина?

Я использую MS SQL Server 2005

1 Ответ

0 голосов
/ 15 сентября 2011

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

Ваша техника с cast и query довольно дорогая, поэтому мое предположение (я не проверял это) заключается в том, что оптимизатор запросов сокращает условия or, чтобы при попадании он не будет продолжать проверять последовательные условия. Это означает, что вы экономите время, расширяя диапазон дат, потому что меньшее количество строк будет проверено на соответствие всем or условиям.

...