Редагувати: +1 працює в цій ситуації, оскільки виявляється, що FILE_NUMBER
це нульова версія рядка цілого числа. Кращим рішенням для рядків є додавання ''
(порожній рядок), оскільки додавання значення може впливати на порядок або для чисел додавати щось, що є константою, але містить недетерміновану функцію, наприклад sign(rand()+1)
. Ідея "зламати сорт" все ще справедлива тут, якраз в тому, що мій метод не був ідеальним.
+1
Ні, я не маю на увазі, що я згоден ні з чим, я маю на увазі це як рішення. Якщо ви зміните свій запит, ORDER BY cj.FILE_NUMBER + 1
тоді TOP 1
засіб буде поводитися інакше.
Розумієте, якщо впорядкований запит встановлений для малого рядка, система намагатиметься споживати дані для того, щоб уникнути наявності оператора Сортування. Це також дозволить уникнути побудови хеш-таблиці, вважаючи, що, ймовірно, не потрібно робити занадто багато роботи, щоб знайти цей перший рядок. У вашому випадку це неправильно - з товщини цих стрілок, схоже, що для знаходження однієї відповідності потрібно споживати багато даних.
Товщина цих стрілок говорить про те, що ваша DOCUMENT_QUEUE
таблиця (DQ) набагато менша, ніж ваша CORRESPONDENCE_JOURNAL
(CJ). І що найкращим планом насправді було б перевірити рядки DQ, поки не буде знайдено рядок CJ. Дійсно, саме це зробив Оптимізатор запитів (QO), якби у нього не було цього прискіпливого ORDER BY
, це добре підтримується індексом покриття на CJ.
Отже, якщо ви ORDER BY
повністю відмовилися , я очікую, що ви отримаєте план, який передбачає вкладений цикл, перебираючи рядки в DQ, шукаючи CJ, щоб переконатися, що рядок існує. І з TOP 1
цим це припиниться після того, як буде виведено один ряд.
Але якщо вам дійсно потрібен перший рядок для FILE_NUMBER
того, то ви можете підманути систему, щоб ігнорувати той індекс, який здається (неправильно) таким корисним, виконуючи ORDER BY CJ.FILE_NUMBER+1
- який, як ми знаємо, буде зберігати той самий порядок, що і раніше, але важливо QO не робить. QO зосередить увагу на тому, щоб викласти весь набір, щоб оператор Top N Sort був задоволений. Цей метод повинен створити план, який містить оператора «Обчислити скаляр» для визначення значення для замовлення та оператора «Сортування вгорі N» для отримання першого рядка. Але праворуч від них ви повинні побачити приємну вкладену петлю, що робить багато шукань на CJ. І краща продуктивність, ніж біг через велику таблицю рядків, яка не відповідає нічого в DQ.
Hash Match не обов'язково жахливий, але якщо набір рядків, які ви повертаєтеся з DQ, набагато менший, ніж CJ (як я б очікував, що це буде), то Hash Match буде сканувати набагато більше CJ ніж це потрібно.
Примітка. Я використовував +1 замість +0, оскільки оптимізатор запитів, ймовірно, визнає, що +0 нічого не змінює. Звичайно, те саме може застосуватись і до +1, якщо не зараз, то в якийсь момент майбутнього.
DOCUMENT_ID
відносини між двома таблицями (або чи має кожен запис уCORRESPONDENCE_JOURNAL
відповідний записDOCUMENT_QUEUE
)?