Pregunta

Entiendo que la opción WITH RECOMPILE obliga al optimizador a reconstruir el plan de consulta para los procesos almacenados, pero ¿cuándo querría que sucediera?

¿Cuáles son algunas reglas generales sobre cuándo usar la opción WITH RECOMPILE WITH y cuándo no?

¿Cuál es la sobrecarga efectiva asociada con solo ponerlo en cada sproc?

¿Fue útil?

Solución

Como han dicho otros, no desea simplemente incluir WITH RECOMPILE en cada proceso almacenado como una cuestión de hábito. Al hacerlo, estaría eliminando uno de los principales beneficios de los procedimientos almacenados: el hecho de que guarda el plan de consulta.

¿Por qué es potencialmente un gran problema? Calcular un plan de consulta es mucho más intensivo que compilar código de procedimiento regular. Debido a que la sintaxis de una declaración SQL solo especifica lo que quiere, y no (generalmente) cómo obtenerla, eso le permite a la base de datos un amplio grado de flexibilidad al crear plan (es decir, las instrucciones paso a paso para recopilar y modificar datos en realidad). Hay muchos trucos " " El preprocesador de consultas de la base de datos puede hacer y las elecciones que puede hacer: qué orden de unir las tablas, qué índices utilizar, si aplicar las cláusulas WHERE antes o después de las combinaciones, etc.

Para una simple sentencia SELECT, puede que no haga una diferencia, pero para cualquier consulta no trivial, la base de datos pasará un tiempo serio (medido en milisegundos, en lugar de los microsegundos habituales) para generar un plan optimo Para consultas realmente complejas, ni siquiera puede garantizar un plan óptimo , solo tiene que usar heurísticas para crear un plan bastante bueno . Entonces, al obligarlo a compilar cada vez, le dices que tiene que pasar por ese proceso una y otra vez, incluso si el plan que tenía antes era perfectamente bueno.

Dependiendo del proveedor, debe haber activadores automáticos para recompilar los planes de consulta, por ejemplo, si las estadísticas en una tabla cambian significativamente (por ejemplo, el histograma de valores en una determinada columna comienza uniformemente distribuido a lo largo del tiempo y se vuelve altamente sesgado). ), entonces el DB debería notar eso y recompilar el plan. Pero en términos generales, los implementadores de una base de datos serán más inteligentes al respecto que usted en general.

Como con todo lo relacionado con el rendimiento, no tome tomas en la oscuridad; averigüe dónde están los cuellos de botella que cuestan el 90% de su rendimiento y resuélvalos primero.

Otros consejos

Ponerlo en cada procedimiento almacenado NO es una buena idea, porque compilar un plan de consulta es una operación relativamente costosa y no verá ningún beneficio de los planes de consulta que se almacenan en caché y se reutilizan.

El caso de una cláusula dinámica donde se construye dentro de un procedimiento almacenado puede manejarse utilizando sp_executesql para ejecutar el TSQL en lugar de agregar WITH RECOMPILE al procedimiento almacenado.

Otra solución (SQL Server 2005 en adelante) es usar una sugerencia con parámetros específicos utilizando la sugerencia OPTIMIZE FOR . Esto funciona bien si los valores en las filas son estáticos.

SQL Server 2008 ha introducido un característica poco conocida llamada " OPTIMIZAR PARA DESCONOCIDO " ;:

  

Esta sugerencia dirige el optimizador de consultas.   Para utilizar los algoritmos estándar que tiene.   Siempre usado si no hay valores de parámetros.   había sido pasado a la consulta en absoluto.   En este caso se verá el optimizador.   en todos los datos estadísticos disponibles para   llegar a una determinación de lo que el   valores de las variables locales utilizados para   generar el queryplan debe ser,   en lugar de mirar lo específico   valores de parámetros que se pasaron a   la consulta por la aplicación.

El uso más común es cuando puedes tener una cláusula WHERE dinámica en un procedimiento ... no querrías que ese plan de consulta en particular se compile y guarde para ejecuciones posteriores, ya que puede que no sea exactamente la misma cláusula la próxima vez que se llame al procedimiento.

En general, una alternativa mucho mejor para WITH RECOMPILE es OPTION (RECOMPILE) Como puede ver en la explicación a continuación, tomada de la respuesta de esta pregunta aquí

  

Cuando se encuentra un problema de sensibilidad de parámetros, una pieza común de   El consejo en los foros y en los sitios de preguntas y respuestas (A) es para " utilizar recompilar " (asumiendo la   otras opciones de ajuste presentadas anteriormente no son adecuadas). Desafortunadamente,   ese consejo a menudo se malinterpreta para significar agregar CON RECOMPILE   Opción al procedimiento almacenado.

     

El uso de WITH RECOMPILE nos devuelve efectivamente a SQL Server 2000   comportamiento, donde todo el procedimiento almacenado se compila en cada   ejecución. Una mejor alternativa, en SQL Server 2005 y posteriores, es   use la sugerencia de consulta OPCIÓN (RECOMPILE) solo en la declaración que   sufre el problema de sniffing de parámetros. Esta consulta insinúa resultados   en una recompilación de la declaración problemática solamente; planes de ejecución   Para otras declaraciones dentro del procedimiento almacenado se almacenan en caché y se reutilizan.   como normal.

     

Usar WITH RECOMPILE también significa el plan compilado para el almacenamiento   El procedimiento no está en caché. Como resultado, ninguna información de rendimiento es   mantenido en DMV como sys.dm_exec_query_stats. Utilizando la consulta   en lugar de una sugerencia, significa que un plan compilado se puede almacenar en caché y el rendimiento   La información está disponible en los DMV (aunque se limita a los más   Ejecución reciente, solo para la sentencia afectada).

     

Para instancias que ejecuten al menos SQL Server 2008 compilación 2746 (Servicio   El paquete 1 con la actualización acumulativa 5), ??utilizando la OPCIÓN (RECOMPILE) tiene otra   ventaja significativa sobre CON RECOMPILE: solo OPCION (RECOMPILE)   habilita la optimización de incrustación de parámetros.

Solo se debe utilizar cuando las pruebas con datos representativos y el contexto demuestran que la operación sin produce produce planes de consulta no válidos (independientemente de las posibles razones). No asuma de antemano (sin probar) que un SP no se optimizará correctamente.

Excepción exclusiva solo para invocación manual (es decir, no lo codifique en el SP): cuando sabe que ha alterado sustancialmente el carácter de las tablas de destino. p.ej. TRUNCATE, GRANDES CARGOS, etc.

Es otra oportunidad para una optimización prematura.

Nota: Tengo muchos puntos. Si un usuario nuevo envía la misma respuesta a continuación, y usted acepta, valide las de ellos.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top