1. Ing. Eduardo Castro, PhD
Microsoft SQL Server MVP
PASS Regional Mentor
PASS Global Board of Directors Advisor
ecastro@simsasys.com
http://www.youtube.com/eduardocastrom
SQL Server Query
Processor
5. Agenda
• SQL Server engine architecture
• Query execution
• Showplan
• Iteradores de SQL
6. SQL Server Engine
Arquitectura de Alto Nivel
Query Execution
(Query Operators, Memory
Grants, Parallelism, Showplan)
Storage Engine
(Access Methods, Buffer Pool, Locking, Transactions, …)
SQL-OS
(Threads, Memory Management, Synchronization, …)
Query Optimization
(Plan Generation, View Matching,
Statistics, Costing)
LanguageProcessing
(Parse/Bind, Statement/Batch Execution, Plan Cache)
Utilities
(DBCC,Backup/Restore,BCP,…)
Metadata,TypeSystem,
ExpressionServices
7. Introducción al Query Optimizer
En el núcleo del motor de base de datos de SQL Server
hay dos componentes principales: el motor de
almacenamiento motor y el procesador de consultas,
también llamado el motor relacional.
El motor de almacenamiento es responsable de la lectura
de datos entre el disco y la memoria de manera que se
optimice concurrencia mientras mantiene la integridad de
los datos.
El procesador de consultas, como sugiere el nombre,
acepta todas las consultas a SQL Server, idea un plan para
su óptima ejecución, y luego ejecuta el plan y ofrece los
resultados requeridos.
Inside the SQL Server Query Optimizer. Benjamin Nevarez.
8. Introducción al Query Optimizer
Para cada query que recibe, el trabajo del procesador de
consultas es idear un plan, tan pronto como sea posible,
que describa la mejor manera posible (o, al menos, una
forma eficiente) de ejecutar dicha consulta.
Su segundo trabajo es ejecutar la consulta de acuerdo con
ese plan.
Cada una de estas tareas se delega en un componente
separado dentro del procesador de consultas; el
optimizador de consultas diseña el plan y luego lo pasa al
motor de ejecución, que realmente ejecutar el plan y
obtiene los resultados de la base de datos.
Inside the SQL Server Query Optimizer. Benjamin Nevarez.
9. El optimizador de consultas
SQL es un lenguaje declarativo de alto nivel
10. Optimización de consultas en pocas
palabras
Instrucción
SQL
Plan de
ejecución
• Los optimizadores de consultas comerciales no tratan de
encontrar la "mejor" plan.
• En lugar de ello, tratan de encontrar un plan "suficientemente
bueno" rápidamente.
12. Cómo funciona el procesamiento de consultas
PlanCache
Generate ExecutablePlan
Execute
Fix Memory Grant &DoP
Auto-Param
Bind, ExpandViews
NotFound
Parse
Query Optimization
Return Plans toCache
NewStatement
LanguageProcessing
(Parse/Bind, Statement/Batch Execution, PlanCache)
Found Executable FoundCompiled
Plan Plan
QueryOptimization QueryExecution
(Plan Generation,View (QueryOperators,
Matching,Statistics, MemoryGrants,
Costing) Parallelism,Showplan)
13. SQL Server Query Optimizer
Basado en el Cascades Framework
Basado en transformación, enfoque top-down
Optimization = Tasks + Memo
( Programs = Algorithms + Data Structures )
Completamente basado en costos
Flexible y con extensiones
Se pueden agregar nuevos operadores y reglas
SQL
Query
Parsing,
Validation
Normalization
(predicate unfolding,
join collapsing, view
substitution, etc.)
Cost-based
Optimization
Execution
Plan
14. Generación de planes de ejecución
candidatos
El propósito básico del optimizador de consultas es
encontrar un plan de ejecución eficiente
para su búsqueda.
Incluso para las consultas relativamente simples, puede
haber un gran número de diferentes caminos acceder a los
datos para producir el mismo resultado final.
El Optimizador de Consultas tiene que seleccionar el mejor
plan posible de un gran número planes candidatos, y es
importante que haga una buena elección, ya que el tiempo
necesario para volver los resultados al usuario pueden
variar mucho, dependiendo de qué plan es seleccionado.
Inside the SQL Server Query Optimizer. Benjamin Nevarez.
15. Generación de planes de ejecución
candidatos
El optimizador de consultas debe lograr un equilibrio entre
el tiempo de optimización y calidad del plan.
Por ejemplo, si el optimizador de consultas gasta un
segundo hallazgo un buen lo suficientemente plan de que
ejecuta en un minuto, entonces no tiene sentido tratar de
encontrar el plan perfecto o más plan óptimo, si esto va a
tomar cinco minutos de tiempo de optimización, más el
tiempo de ejecución.
Así que SQL Server no realiza una búsqueda exhaustiva,
sino que intenta encontrar un plan eficiente tan
rápidamente como sea posible.
Inside the SQL Server Query Optimizer. Benjamin Nevarez.
16. Generación de planes de ejecución
candidatos
Con el fin de explorar el espacio de búsqueda, el
optimizador de consultas utiliza reglas de transformación y
heurística.
Los generación de planes de ejecución de candidatos se
realiza dentro del optimizador de consultas usando reglas
de transformación, y con el uso de heurísticas limita el
número de opciones, con el fin de mantener el tiempo de
optimización razonable.
Los planes candidatos son almacenado en la memoria
durante la optimización, en un componente llamado Memo.
Inside the SQL Server Query Optimizer. Benjamin Nevarez.
17. Planteamiento del Problema
Workload Database
Configuration
Physical
Design Tool
Conjunto de
estructuras físicas
(es decir, índices y
vistas) que hacen
que las cargas de
trabajo similares
ejecutar lo más
rápido posible
18. Database Tuning Advisor Yukon
Carga de trabajo
Comprimir
la carga de
trabajo
Selección de
candidatos
(Por consulta)
Enumeración
Tiempo?
Sí
No
La fusión
Recomendación
Sintonización
Cliente
...
Optimizador
de consultas Base de datos
Servidor
Y si
API
Metadatos
- Crear hipotético Índice / Vista.
- Optimizar consultas con
respecto a las configuraciones
hipotéticas.
19. Nueva Arquitectura
Instrumentación el optimizador de consultas.
Estrategia de búsqueda basado en relaxations.
…
Query
Optimizer
Database
Server
What-if
API
Metadata
Relaxation
Time?
Yes
No
Recommendation
Tuning
Client
Workload
Request
Identification
Get Optimal Configuration
(per query)
Requests
API
20. El procesamiento de consultas
Query execution, plan caching - la consulta
es ejecutada por el motor de ejecución,
según el plan seleccionado; el plan puede
ser almacenado en la memoria caché.
Inside the SQL Server Query Optimizer. Benjamin Nevarez.
21. El proceso de optimización
El proceso de optimización, es la generación de
los planes de ejecución candidatos
y la selección de los mejores de estos planes de
acuerdo a su costo.
El optimizador de consultas de SQL Server
utiliza un modelo de estimación de costos
para estimar el costo de cada uno de los planes
de candidatos.
Inside the SQL Server Query Optimizer. Benjamin Nevarez.
22. El proceso de optimización
Análisis sintáctico (Parsing) / Binding (antes de la
optimización)
Simplificación
Análisis de los Join - Orders
Generación de Plan de trivial
Fases de optimización
Search 0
Search 1
Search 2
Ejecución
23. Proceso con más detalles
"Optimizar" toma un árbol de consulta válido y genera un
plan de consulta válida
Si la compilación toma un tiempo, esto es casi siempre en
este fase donde ocurre
Los diferentes planes son considerados y el que se
considera mejor es elegido
La búsqueda del plan es una heurística para mantener
reducir el tiempo de elección de plan lo más posible.
5
SQL Tree Query Plan
Parse Bind Optimize
24. Optimization: Trivial Plan Optimization
Se presenta en casos en donde el Query es
tan sencillo que no es necesario optimizar la
consulta
SELECT * FROM dbo.Users WHERE UserId =
1
Si el UserID es un clustered key, solo hay
que hacer un Seek y devolver los datos
25. Optimization: Full Optimization: Search 0
Se busca un plan bueno en el mínimo del
tiempo
Se utilizan heurísticas y genera un conjunto de
posibles opciones iniciando con el menor
número de tablas
Si en este paso no se encuentra un plan lo
suficientemente bueno se procede con el
siguiente paso
Podría que ese paso sea “skipped” y que
optimizar pase directamente al siguiente paso
26. Optimization: Full Optimization: Search 1
Es paso es conocido como el Quick Plan
En este paso se utilizan reglas de conersión y
algunas permutaciones
Si en este paso no se encuentra un plan lo
suficientemente bueno se repite para encontrar
un plan paralelo
Al final se comparan los planes para elegir uno
Si ninguno cumple con los “ optimizer internal
thresholds” entonces se continúa con el
siguiente paso
27. Optimization: Full Optimization: Search 2
Se conoce como “Full”
En este paso se tiene que generar un plan
incluso aunque no se encuentre un plan lo
suficientemente bueno
Se utiliza para query complejos
28. ¿Qué es un árbol de la consulta?
El plan de consulta de salida es un árbol
En el interior del optimizador, hay árboles lógicos y
físicos.
Conceptos árbol lógico:
JOIN, WHERE, GROUP BY
Conceptos árbol físicos:
Hash/Loop/Merge Join, Filter, …
6
BA
JOIN (A.a = B.b)
WHERE (A.c = 5)
GROUP BY (B.d)
29. Otro nivel más profundo ...
9
Query Optimizer
Algebrizer
(Parse/
Bind)
Query
Execution
Simplification
Auto-CreateStats
DeriveCardinality
FixInitialJoinOrder
Exploration
0 1 2
Stage
CopyOut
Convertto
Query
ExecTree
TrivialPlan
• Se ejecutan operaciones en un orden específico para reducir la complejidad
y el costo de tiempo de ejecución
• "Simplificación" limpia el árbol basado en reglas en una forma que
preferimos. (Predicate Pushdown, Contradiction Detection)
• Cardinalidad y cálculo de costos proporcionan un ranking para cada plan
• "Exploración" examina muchos planes a la vez para encontrar el plan de
menor costo
30. El procesamiento de consultas
Parsing and binding - La consulta es parsed and bound.
Asumiendo que la consulta es válida, la salida de esta fase
es un árbol lógico
Con cada nodo en el árbol representa una
operación lógica que la consulta debe llevar a cabo, como
la lectura de una tabla en particular hacer un inner join.
Un planes de ejecución es, en esencia, un conjunto de
operaciones físicas por ejemplo, Index Seek, a Nested Loops Join
que se pueden realizar para producir el resultado deseado, tal como
se describe por el árbol lógico
Inside the SQL Server Query Optimizer. Benjamin Nevarez.
31. Análisis sintáctico (Parsing) / Binding
El “parsing” se asegura
de que la consulta T-SQL
tiene una sintaxis válida
“Binding” se refiere
principalmente a la
resolución de nombres
Utiliza la información de
consulta para construir un
árbol de operadores
relacionales
32. El procesamiento de consultas
Optimización de consultas - El árbol lógico se usa
entonces para ejecutar la optimización de la consulta, que
a grandes rasgos se compone de los siguientes dos pasos:
Generación de posibles planes de ejecución - Utilizando el
árbol lógico, el optimizador elabora una serie de posibles formas
de ejecutar la consulta, es decir, un número de posibles planes
de ejecución
Evaluación de costo de cada plan - Mientras que el
optimizador de consultas no genera cada posible plan de
ejecución, sí evalúa el costo de los recursos y el tiempo de cada
plan; el plan que el optimizador de consultas considera que tiene
el menor costo es seleccionado, y lo pasa al motor de ejecución.
Inside the SQL Server Query Optimizer. Benjamin Nevarez.
34. Propiedades
El Optimizador de crea gran cantidad de
información en cada nodo del árbol
Esta información se conoce como "Propiedades".
Esto se realiza sobre los árboles lógicos y árboles
físicos
Ejemplo propiedad lógica: columnas primarias, rangos
válidos para cada columna utilizada en una consulta
Ejemplo de la propiedad física: Ordenar columnas
Hay propiedades para cada punto (partitioning, distributed
query)
Propiedades ayuda a determiner cuales
transformaciones son consideradas en la búsqueda
del conjunto de posibles planes de ejecución
10
35. Simplificación
Reduce el árbol de consulta en una forma más simple con
el fin de hacer más fácil el proceso de optimización
Algunas de las simplificaciones incluyen:
• Por ejemplo se quitan los inner joins y outer joins
redundantes.
• Los filtros en la cláusulas WHERE se empujan hacia abajo
en el árbol de la consulta con el fin de habilitar el filtrado de
datos temprana (predicado desplazamiento descendente)
• Las contradicciones se detectan y eliminan
37. Ejemplo de detección de contradicción
SQL deriva propiedades de restricción de dominio en cada columna, en
cada consulta en cada nodo
Al hacer una combinación, hacemos una combinación de las dominios
válidos
Podemos detectar cuando las condiciones son siempre falsas y luego
convertir todo ese árbol zero-row fake table.
13
38. Reglas
Los planes son exploradas utilizando
"reglas" que transformar el árbol de una
forma u otra
Las reglas detectan patronese n el árbol y
crean nuevos patrones. Patrones
describen fragmentos de árboles de arriba
hacia abajo, pero no son árboles de
consulta completos
Las reglas pueden ir de lógico -> lógica o
lógico -> física
SQL cuenta con muchas, muchas reglas
14
ba
join
ab
join
Join Commute
ab
Hash Join
Join to Hash Join
ab
join
39. Reglas de transformación
Se utiliza para explorar el espacio de búsqueda
Reglas de exploración (reglas de transformación lógica. Generan
alternativas equivalentes lógicos
Conmutatividad
A join B – > B join A
Asociatividad
(A join B) join C – > A join (B join C)
Las reglas de implementación (reglas de transformación física)
Obtener alternativas físicas
Join to Sort Merge Join
A join B – > A Merge Join B
40. Reglas de transformación
La aplicación de transformaciones no necesariamente reduce el costo
de las alternativas generadas
El costo se calcula después (únicamente las alternativas físicas se les
asigna un costo)
42. El “Memo”
El Optimizador no materializa todas las
alternativas
El Memo rápidamente identifica y almacena
equivalentes sub-árboles
Almacenado en "grupos"
Los grupos apuntan a otros grupos para que
podamos compartir árboles
El top-down rule framework hace que este "fácil" de
hacer
Esto nos permite de buscar muchos más planes
en la misma cantidad de tiempo / espacio
18
43. El Memo
Estructura de búsqueda de datos que se
utiliza para almacenar las alternativas que
son generadas y analizadas por el
optimizador de consultas
Una nueva estructura memo se crea para
cada optimización
El optimizador de consultas copia las
expresiones lógicas del árbol búsqueda
original en la estructura del memo
44. The Memo - Search Space Memory
Almacena de forma compresa todas la alternativas exploradas
(AND-OR graph)
Agruga juntos los árboles de operadores equivalentes y sus
planes de ejecución
Maneja la detección de duplicados, administración de
propiedades y de costos, etc.
1) SELECT (b>20, )
b>20
S
1) SELECT (a<10, )
a<10
R
2) JOIN (x=y, , )
1) SELECT (a<10, )a<10 b>20
R S
1) GET(S)S1) GET(R)R
b>20R
S
1) JOIN (x=y, , )
2) ...
3) ...
Groups
Expressions
45. Initialize Memo
Optimize Root Group
Optimize Group
Explore Group
Obtain enforcers and
implementation rules for all
expressions
Apply Rules by Promise
Optimize Inputs
Obtain optimization context
Optimize children groups
Calculate costs, pick best
Apply Rule
Pruning checks
Generate bindings, substitutes
Restrict ruleset
optimizing?Opt Inputs:Explore
Explore Expression
Apply-always rules
Explore Inputs
Rest of Apply-always Rules
Other Rules by Promise
Explore Group
For each expression
-Get Guidance
-Explore Expression.
Tareas de optimización
49. Codificación de alternativas
22
tabla de alternativas (MEMO)
insertar
el árbol de entrada
0 – 1 join 4
1 – 2 join 3
2 – {a}
3 – {b}
4 – {c}
join
ba
join c
SELECT * FROM A
INNER JOIN B ON
A.a=B.b INNER JOIN C
on A.a = C.c;
51. Estimación de la cardinalidad
Las estadísticas de los objetos y la cardinalidad de las tablas son
la Fuente para la estimización de cardinalidad. Incluyen:
histogramas
frecuencias / densidades de multi-columnas
Arboles Trie para la estimación LIKE
Cardinalidad se deriva "de abajo hacia arriba" para cada
operador
Hay muchos problemas muy difíciles en este tema
Ejemplo: cross-table con datos altamente correlacionados
Supuestos de la simplificación
Independencia estadística
Distribuciones de datos uniformes dentro de los rangos.
SET STATISTICS PROFILE ON – se utiliza para la mayoría de
los problemas de rendimiento de consultas para determinar si las
estimaciones de cardinalidad son buenas
24
52. Cálculo de los costos
Sobre la base de estimación de la cardinalidad (por lo que debe ser el
adecuado para que esto tenga sentido)
Se calcula el costo para cada árbol físico
Cosas que incluimos en cuesta:
¿Cuánto IO (secuencial, aleatorio), CPU, espacio en la memoria para páginas
de búfer
datos de DOP / Particiones
Las cosas que no incluyen en el cálculo de costos:
Velocidad de la CPU, IO Subsistema de velocidad
Las fórmulas de cálculo del coste fueron originalmente el # de
segundos en la máquina de Nick
supuestos:
No nos costo de CPU / IO por separado para cada instalación simplificar
consultas de depuración
tampón frío grupo de caché - suponemos filas no están en el grupo de búfer
cuando la consulta se inicia
Uniformidad - IO a partir de una serie de seeks se distribuyen aleatoriamente a
través de un B-Tree
25
53. Búsqueda dinámica / Etapas
El optimizador hace cosas de lujo para reducir el
tiempo de compilación
1. Se detiene de buscar alternativas que conocemos
que cuesta más que la mejor solución encontrada
hasta el momento
2. Dividimos reglas en grupos basados en el costo
versus el beneficio (reglas más costosas o de
dominio específico se ejecutan en etapas
posteriores). Se termina la optimización si hemos
encontrado un plan "suficientemente bueno"
3. Limitamos el optimizador para detener la
optimización después de un cierto número de
reglas
26
54. Index Matching
SQL convierte predicados en las operaciones de
índice (Seeks). Estos predicados se denominan "
SARGable“
Una operación es SARGable si se puede utilizar un
índice para mejorar el desempeño
Algunos predicados no pueden ser convertidos -
Non-SARGable
Algunos predicados Non-SARGable se evalúan
dentro del motor de almacenamiento. ( "Pushed
Non-SARG Predicates ")
Esta optimización reduce la cantidad de instrucciones
Sólo las expresiones “baratas" se puede hacer de esta
manera
27
55. Index Matching
Se reescriben las reglas para mover las
operaciones lo más cerca posible hacia las
hojas del árbol para permitir el index matching
Ejemplos
SARGable : DÓNDE columna = 5
Non-SARGable : DONDE convert (columna, String) =
"5“
Sargable operators: =, >, <, >=, <=, BETWEEN, LIKE,
IS [NOT] NULL, EXISTS
Sargable operators que raramente aumentar el
desempeño: <>, IN, OR, NOT IN, NOT EXISTS, NOT
LIKE
27
56. Más sobre Index Matching
Sólo la indexación no suele ser suficiente - también se quiere evaluar si
un índice es “covering index".
Ejemplo
CREATE INDEX i1 on T(col1)
SELECT col1, col2 FROM T
(Index i1 is not covering scan)
Non-covering indexes normalmente tienen que hacer búsquedas a la
tabla base (random IO es lento)
SQL 2005 agregar la cláusula INCLUDE que le permite añadir
columnas para hacer indexes covering
Para evitar / reducir este costo, el optimizador considera que las
estrategias como ésta al momento de elejir los índices de planes:
1. Seek del Clustered Index
2. Seek NC1 and join con otros NCIs
3. Hacer 2 y después buscar Heap/CI para obtener el resto de las columnas
Missing Index DMVs pueden ayudar a sugerir covering indexes
28
57. Ejemplos Index Matching
29
Primer ejemplo – Basic
SARGable Seek + Fetch
para obtener columnas del
Heap
Segundo ejemplo– NOT
SARGable – ver que es un
pushed predicate Scan
58. Fases de optimización - Optimización
completa
Search 0, Transaction Processing phase
Search 1, Quick Plan phase
Search 2, Full Optimization
62. El proceso de optimización
La optimización de consultas es el proceso e mapear las
operaciones lógicas del árbol original en su equivalente de
operaciones físicas, las cuales serán ejecutadas por el
motor de ejecución.
La funcionalidad del motor de ejecución aplicar los planes
de ejecución que son creados por el optimizador de
consultas.
El motor de ejecución implementa cierto número de
diferentes algoritmos, y a partir de estos algoritmos que el
optimizador de consultas debe elegir, cómo formula los
planes de ejecución.
Inside the SQL Server Query Optimizer. Benjamin Nevarez.
63. El proceso de optimización
Se traducen las operaciones lógicas originales en el
operaciones físicas que el motor de ejecución es
capaz de realizar, y los planes de ejecución incluyen
tanto las operaciones lógicas y físicas.
Algunos operaciones lógicas, como un Sort se
traducen a la misma operación física, mientras que
otras operaciones lógicas se traducen a varias
operaciones físicas.
Por ejemplo, una join lógico se puede traducir en un
Nested Loops Join, Merge Join, o Hash Join .
Inside the SQL Server Query Optimizer. Benjamin Nevarez.
64. El proceso de optimización
El producto final del proceso de optimización
de la consulta es un plan de ejecución: un
árbol que consiste de un número de
operadores físicos, que contienen los
algoritmos que serán ejecutados por el motor
de ejecución con el fin de obtener los
resultados deseados desde
la base de datos.
Inside the SQL Server Query Optimizer. Benjamin Nevarez.
65. El procesamiento de consultas
Inside the SQL Server Query Optimizer. Benjamin Nevarez.
66. Flujo de ejecución de Queries
• Query plans son árboles de iteración
• Iterador = unidad básica del query plan execution
• Cada iterador tiene 0, 1, 2, o N hijos
• Los métodos principales de cada iterador son:
– Open
– GetRow
– Close
• Los flujos de control van hacia abajo en el árbol
• Data flows (se llenan) hacia arriba en el árbol
67. Consulta de ejemplo
SELECT l_orderkey, l_linenumber, o_orderstatus
FROM lineitem JOIN orders ON l_orderkey = o_orderkey
WHERE l_suppkey < 2000 AND l_partkey < 2000
lineitem
l_suppkey<2000, l_partkey<2000
l_orderkey=o_orderkey
orders
l_orderkey, l_linenumber, o_orderstatus
Obtenga toda la información acerca line-items que están filtrados
por proveedores y partes
68. Tipos de iteradores
• Insert, update, and delete
• Top
• Compute scalar
• Filter
• Concatenation
• Sequence
• Scan and seek
• Joins
• Aggregates
• Sorts
• Spools
• Parallelism
69. Showplan
• Muestra el plan de ejecución
• Excelente herramienta ...
– Para entender qué es lo que está haciendo SQL Server
– Para diagnosticar problemas de desempeño
• Un montón de Estadísticas ...
– Cantidad Estimada y real de fila
• Gráfica, texto, y XML versiones
– XML desde SQL Servidor 2005
70. Gráfico vs XML
Gráfico
Vista con base en íconos
Da una vista general
Fácil identificar los iteradores más costosos
Provee ayuda para cada iterador
XML
Vista gráfica sencilla desde SQL Server 2005
Muestra mayor detalle
Más difícil de leer que los planes gráficos
| --StreamAgregado
| --sort
| --NestedLoops
| Índice --Clustered
Buscar
| --indexVerk
...
<RelOp NodeID= "0"
...>
<StreamAggregate>
<RelOp NodeID= "1"
...>
<Ordenar...>
...
71. Leyendo planes
• Gráfico
– Cada icono representa un iterador en el árbol
– Estructura del árbol estructura y flujos de datos están representados por flechas
que conectan los iconos
– Más información es disponible en el información sobre herramientas y en el
"propiedades" cristal
• XML
– Un elemento por iterador más los elementos adicionales para otra información
– Estructura del árbol es representado por anidamiento de elementos
– Flujos de datos están en los elementos más exteriores
72. Showplan ejemplos
DECLARE @Date DATETIME
SET @Date = '1996-07-04'
SELECT L_SHIPDATE, COUNT_BIG(*)
FROM LINEITEM JOIN ORDERS ON L_ORDERKEY = O_ORDERKEY
WHERE O_ORDERDATE = @Date
GROUP BY L_SHIPDATE
ORDER BY L_SHIPDATE
79. Text/XML plan options
SQL Profiler y DMVs también muestran los planes
Command Execute
Query?
Display
Estimated
Row Counts
& Stats
Display
Actual
Row
Counts
Text
plan
SET SHOWPLAN_TEXT ON No No No
SET SHOWPLAN_ALL ON No Yes No
SET STATISTICS PROFILE ON Yes Yes Yes
XML
plan
SET SHOWPLAN_XML ON No Yes No
SET STATISTICS XML ON Yes Yes Yes
80. Iteradores comunes
• Scans and seeks
• Join iterators
– Nested loops join
– Merge join
– Hash join
• Aggregation iterators
– Stream aggregrate
– Hash aggregate
• Los iteradores no son buenos ni males
• No existe “el mejor” join o tipo de agregación
• Cada iterador funciona bien dependiendo del escenario
81. Scans and seeks
• Scans devuelve toda una tabla o un índice
– Los scan de índices pueden ser con o sin orden
• Seeks devuelve de forma eficiente las filas de
uno o más rangos de un índice
– Los seeks de un índice siempre son ordenados
82. Index scan vs. index seek
Select Price from Orders where OrderKey = 2
Index Scan
Where OrderKey = 2
Index Seek
Where OrderKey = 2
OrderKey Price
1 86.00
2 17.00
3 88.00
4 17.00
5 96.00
6 22.00
7 74.00
8 94.00
9 56.00
… …
1 86.00
2 17.00
3 88.00
… …
2 17.00
83. Nested loops join
• Algoritmo básico:
1. Obtener una fila de la entrada izquierda
2. Obtener todas filas de la entrada derecha que corresponde a la fila
de la entrada izquierda
3. Cuando ya no hay más filas que hagan match desde la entrada
derecha, obtenga la siguiente fila de la entrada izquierda y repita
• Parámetros correlacionados
– Datos de la entrada izquierda afecta los datos devuelto por la
entrada derecha (es decir, paso 2 depende de paso 1)
– Si no se tienen parámetros correlacionados cada ejecución de la
entrada derecha se produce el mismo resultado
84. Nested loops join example
Select C.Name, O.Price
from Cust C join Orders O
on O.CustKey = C.CustKey
where C.City = ‘Boston’
Nested
Loop Join
Index Seek
Cust
Where C.City =
‘Boston’
Index Seek
Orders
On O.CustKey =
C.CustKey
No rows match CustKey = 6
4 88.00
5 86.00
5 94.00
5 56.00
4 Boston Alice
5 Boston Bob
6 Boston Cathy
Alice 88.00
Bob 86.00
Bob 94.00
Bob 56.00
85. Nested loops join
• El único tipo join...
– Que soporta predicados de inequidad
• La entrada derecha puede ser un index seek o un subplan complejo
• Optimizaciones:
– Usar índices para optimizar la selección de filas que hacen match de la entrada
derecha filas (Además conocido como una índice unirse a)
– Usar lazy spool en la entrada derecha si esperamos duplicar filas de la entrada
izquierda
• Tips de desempeño:
– Costo es proporcional a la producto de la cardinalidad de las entradas izquierda y
derecha
– En general es mejor para conjuntos de datos pequeños
– Crear un índice para cambiar el producto cartersiano en un index join
– Verifique si se da gran cantidad de I/Os aleatorios
86. Columnas indizadas
• Key columns:
– Conjunto de columnas que puede ser utilizado en un índice
– En un índice compuesto, el orden del columnas importa:
• Determina el ordenamiento del índice
• Solo puede hacer seek en una columna si todas las columnas anteriores tienen
predicados de equidad
– Los non-unique non-clustered index en una tabla con un clustered index
incluye implícitamente el clustered index para las llaves
• Covered columns:
– Conjunto de columnas que pueden ser la salida de un seek o scan del índice
– Heap Index o Clustered Index siempre cubren todas las columnas
– Non-clustered index cubre las columnas llave del índice y si la tabla tiene
clustered index las llaves del clustered index
– Se pueden agregar más columnas durante la creación del índice
87. Bookmark lookup
• Pregunta:
– Lo que pasa si el non-clustered index para un seek no cubre todas
de la columnas necesarias por la consulta?
• Respuesta:
– Look up las columnas extra en el heap o clustered index
– Esta operación es conocida como bookmark lookup
• SQL Server 2000 tenía bookmark lookup iterator
• SQL Server 2005 y 2008 no tienen un bookmark lookup iterator
– En su lugar simplemente unen el non-clustered index con el clustered
index usando un nested loops join
– Parasabersiseusaunbookmark lookup, busque el keyword
“LOOKUP” en el clustered index seek
– Bookmark lookup provoca I/Os aleatorios: afecta el desempeño
88. Bookmark lookup example
Clustered index on OrderKey
Non-clustered index on Custkey
Select Price from Orders where CustKey = 5
Index Seek
Where
CustKey = 5
Nested
Loop Join
Clustered
Index Seek
Select Price
OrderKey CustKey Price
1 5 86.00
2 2 17.00
3 4 88.00
4 9 17.00
5 1 96.00
6 7 22.00
7 8 74.00
8 5 94.00
9 5 56.00
… … …
1 5
8 5
9 5
1 5 86.00
8 5 94.00
9 5 56.00
89. Merge Join
• Requiere al menos un predicado equijoin
• Datos debe estar ordenados en los join keys
– Sort Order debe ser proporcionado por un índice
– Opuede incluir un sort explícito
• Algoritmo Básico :
1. Obtener una fila de las entradas izquierda y derecha
2. Si las filas coinciden devuelva la fila unida
3. De lo contrario, obtenga una nueva fila de cualquier
entrada que sea la más pequeña y repita
90. Merge join
Index Seek
Cust
Where C.City =
‘Boston’
Select C.Name, O.Price
from Cust C join Orders O
on O.CustKey = C.CustKey
where C.City = ‘Boston’
Merge Join
O.CustKey =
C.CustKey
Index Scan
Orders
Cust and Orders indexes ordered by CustKey
2 17.00
4 88.00
5 86.00
5 94.00
5 56.00
7 22.00
4 Boston Alice
5 Boston Bob
6 Boston Cathy
Alice 88.00
Bob 86.00
Bob 94.00
Bob 56.00
91. Merge join
• Optimizaciones:
– One to many join
– Inner join terminates tan pronto como una de las entradas se
termina
• Tips de desempeño:
– Costo es proporcional a la suma de las cardinalidades de las
entradas
– Tiene buen desempeño para entradas grandes y pequeñas
especialmente si el sort order es proveído por un índice
– Si el merge join plan incluye sort explícitos, vigile que no se den
splilling
– No funciona tan bien en paralelo como un hash join
92. Hash join
• Requiere al menos un predicado equijoin
• Algoritmo Básico :
1. Obtener todas filas de la entrada izquierda
2. Construir un in-memory hash table utilizando filas de la
entrada izquierda
3. Obtener todas las filas de la entrada derecha
4. Utilizar el hash table para encontrar coincidencias
• Requiere memoria para construir el hash table
• Si el join se queda sin memoria, porciones las
entradas izquierdas y derechas deben ser
enviadas a disco y manejadas en pasadas distintas
93. Hash Table
Hash join example
Hash Join
Index Seek
Cust
Where C.City =
‘Boston’
Select C.Name,
O.Price from Cust C
join Orders O on
O.CustKey =
C.CustKey where
C.City = ‘Boston’
O.CustKey =
C.CustKey
Table Scan
Orders
Order of Cust and Orders tables does not matter
5 Boston Bob
4 Boston Alice
6 Boston Cathy
5 86.00
2 17.00
4 88.00
9 17.00
5 94.00
5 56.00
Bob 86.00
Alice 88.00
Bob 94.00
Bob 56.00
94. Hash join
• Fuciona como stop and go en la entrada izquierda
• Optimizaciones:
– Construir la tabla hash la entrada más pequeña
– Si el join hace splills, puede hacer switch de las entradas
– Puede utilizar bitmap para descartar entradas de la fila de derecha más
rápido
• Tips de desempeño:
– Costo es proporcional a la suma de las cardinalidades de las entradas
– Generalmente se desempeña bien para conjuntos de datos grandes
– Los parallel hash joins escalan bien
– Verifique no se dén spilling, especialmente múltiples pasadas (utilice el
SQL Profiler)
95. Stream aggregate
• Los datos deben estar ordenados en grupos por la
llave
• El ordenamiento agrupa las filas con llaves iguales
juntas
• Procesa los grupos de uno en uno
• No causa bloqueos o utiliza memoria
• Es eficiente si el sort order es proveído por un índice o
sí el plan incluye ordamientos
• Es la opción para scalar aggregates
96. Stream aggregate example
Select CustKey, sum(Price) from Orders group by CustKey
Index Scan
Stream Agg
Orders index ordered by CustKey
4 88.00
5 86.00
5 94.00
5 56.00
7 22.00
4 88.00
5 236.00
7 22.00
97. Hash aggregate
• Datos no tiene que estar ordenados
• Construye una tabla hash para todos los grupos
• Stop and go
• Al igual que un hash join :
– Requiere memoria, puede utilizar disco si se acaba la memoria
– Generalmente mejor para conjuntos de datos grandes
– Los Parallel hash aggregates escalan bien
• Valores con llaves duplicadas...
– Puede ser malo para un hash join porque no es posible subdividir un
hash bucket que tiene todos duplicados
– Son buenos para un hash aggregate debido a que los duplicados
colapsan dentro una única entrada de la tabla hash
98. Hash Table
Hash aggregate example
Select CustKey, sum(Price) from Orders group by CustKey
Table Scan
Hash Agg
Order of Orders table does not matter
7 22.00
4 88.00
5 236.00
5 86.00
4 88.00
7 22.00
5 94.00
5 56.00
99. Tips de desempeño
• Vigile errores en los cardinality estimates
– Los errores se propagan hacia arriba, debe buscar la raíz de la causa
– Asegúrese que las estadísticas están actualizadas y que son lo más exactas posible
– Evite el uso excesivo de predicatos complejos
• Recomendaciones generales:
– Utilice set based queries
– Evite joining columns con mismatched data types
– Evite outer joins, cross applies, complex sub-queries, dynamic index seeks, …
– Evite dynamic SQL
– Utilice SET STATISTICS IO ON para vigilar si de dan mucha cantidad de I/Os
– Utilice índices como workaround locking, concurrency, and deadlock issues
• OLTP:
– Evite iterados que consuman memoria o que causen bloqueos
– Utilice seeks no scans
• DW :
– Utilice planes paralelos
– Verifique que no se den skews in los planes paralelos
100. Otros planes de ejecución
• Static vs. dynamic index seeks
• Insert, update, y delete plans
– Update por row vs. por index
– Split sort collapse updates
101. Static vs. dynamic index seeks
• Static index seeks
– Los rangos son conocidos y no se traslapan en tiempo de
compilación
– Standalone index seek iterator
• Dynamic index seeks
– Los rangos se traslapan en tipo de de ejecución
– Típicamente se utilzian con predicados OR’ed con T-SQL
o parámetros correlacionados:
• … where State = @p1 or State = @p2
– Sort and merge (merge interval iterator) los rangos
cambian en tiempo de ejecución según sea necesario
103. Merge interval
Select * from T
where [C] between @p1 and @p2 or
[C] between @p3 and @p4 or
[C] between @p5 and @p6
@p1 @p2
@p3 @p4
@p5 @p6
We must not scan this range twice!
104. Merge interval
Sort
Select * from T
where [C] between @p1 and @p2 or
[C] between @p3 and @p4 or
[C] between @p5 and @p6
@p1 @p2
@p5 @p6
@p3 @p4
We must not scan this range twice!
105. Merge interval
Merge
Select * from T
where [C] between @p1 and @p2 or
[C] between @p3 and @p4 or
[C] between @p5 and @p6
@p3 @p4@p1 @p6
Each unique range scanned only once!
106. Insert, update, and delete plans
• Todos los planes de update tienen dos partes:
– Read cursor devuelve las filas para insert, update, or delete
– Write cursor
• Ejecuta el insert, update, o delete
• Mantiene los non-clustered indexes
• También los checks constraints, indexed views, …
• La mayoría de las veces es un único update iterator
107. Per row vs. per index updates
• Per row plans:
– Un único update iterator mantiene todos los índices (lo cual incluye
heap o clustered index y todos los non-clustered indexes)
– Lee una fila de la entrada a la vez y después modifica todos los índices
afectados
• Per index plans:
– El plan tiene un iterador de update separado para cada índice afectado
– Cada iterador de update mantiene sólo un índice
– Lee y pone en spool todas las filas de entrada antes de modificar
cualquier índice
– Aplica todas las modificaciones en un índice a la vez
• Por qué per index?
– Para desempeño en large updates (e.g., sort on index key)
111. Split sort collapse updates
Update T set UniqCol = UniqCol + 1
• Debe asegurarse que los update a los unique indexes
no hacen violaciones de unicidad
• Los iteradores de split, sort, y collapse iterators
reorganizan el flujos de filas a actualizar para
garantizar que no existe violaciones de unicidad
112. Split sort collapse
Update T set UniqCol = UniqCol + 1
Sort
Collapse
Split
Old New
Old New
UniqCol Data
1 X
2 Y
1 2 X
2 3 Y
Del 1 X
Ins 2 X
Del 2 Y
Ins 3 Y
Del 1 X
Del 2 Y
Ins 2 X
Ins 3 Y
Del 1 X
Upd 2 Y X
Ins 3 Y
113. SQL Server 2016 Query Store
Regresiones de
planes
Identificar a los
grandes
consumidores
Evitar riesgos de
upgrades de
SQL Server
Analizar cargas
de trabajo
114. Resumen
• Los iteradores son los bloques básicos del query execution y query plans
• Showplan
– Graphical
– Text
– XML
• Scan vs. seek vs. bookmark lookup
• Existen tres join iterators:
– Nested loopsjoin
– Merge join
– Hashjoin
• Dos aggregation iterators:
– Stream aggregate
– Hash aggregate
115. Referencias
• Libros…
– Inside SQL Server 2005: Query Tuning and Optimization
• Blogs …
– http://blogs.msdn.com/craigfr
– http://blogs.msdn.com/sqlqueryprocessing
• Otras fuentes…
– Books online
– MSDN
– Newsgroups and forums
– Web search