Під час розбору SQL Server викликає, sqllang!DecodeCompOp
щоб визначити тип оператора порівняння, який присутній:
Це відбувається задовго до того, що в оптимізаторі все входить.
Від операторів порівняння (Transact-SQL)
Відстежуючи код за допомогою налагоджувача та публічних символів *, sqllang!DecodeCompOp
повертає значення в регістр eax
** таким чином:
╔════╦══════╗
║ Op ║ Code ║
╠════╬══════╣
║ < ║ 1 ║
║ = ║ 2 ║
║ <= ║ 3 ║
║ !> ║ 3 ║
║ > ║ 4 ║
║ <> ║ 5 ║
║ != ║ 5 ║
║ >= ║ 6 ║
║ !< ║ 6 ║
╚════╩══════╝
!=
і <>
обидва повертають 5, тому вони не відрізняються від усіх наступних операцій (включаючи компіляцію та оптимізацію).
Незважаючи на те, що зазначено вище, можна також (наприклад, використовуючи недокументований прапор трассировки 8605) подивитися на логічне дерево, передане оптимізатору, щоб підтвердити те, що обидва, !=
і <>
відобразити на ScaOp_Comp x_cmpNe
(не рівне порівняння скалярного оператора).
Наприклад:
SELECT P.ProductID FROM Production.Product AS P
WHERE P.ProductID != 4
OPTION (QUERYTRACEON 3604, QUERYTRACEON 8605);
SELECT P.ProductID FROM Production.Product AS P
WHERE P.ProductID <> 4
OPTION (QUERYTRACEON 3604, QUERYTRACEON 8605);
обидва виробляють:
LogOp_Project QCOL: [P] .ProductID
LogOp_Select
LogOp_Get TBL: Production.Product (псевдонім TBL: P)
ScaOp_Comp x_cmpNe
ScaOp_Identifier QCOL: [P] .ProductID
ScaOp_Const TI (int, ML = 4) XVAR (int, не належить, значення = 4)
AncOp_PrjList
Виноски
* Я використовую WinDbg ; доступні інші налагоджувачі. Загальнодоступні символи доступні через звичайний сервер символів Microsoft. Докладніші відомості див. У розділі « Поглиблення в SQL Server» за допомогою Minidumps консультативною командою клієнта SQL Server та налагодження SQL Server з WinDbg - вступ Клауса Ашенбреннера.
** Використання EAX для 32-бітних похідних Intel для повернення значень функції. Звичайно Win32 ABI робить це саме так, і я впевнений, що він успадковує цю практику ще в старі часи MS-DOS, де AX використовувався з тією ж метою - Майкл Кьорлінг