在SQL Server中,动态SQL比静态SQL性能更好吗?
我的一位同事声称,在许多情况下,动态SQL的执行速度比静态SQL快,所以我经常看到到处都是DSQL。除了明显的缺点,比如在运行之前无法检测到错误,而且更难阅读,这是否准确?当我问他为什么一直使用DSQL时,他说: 当静态不会阻止缓存重用时,首选静态;当静态会阻止缓存重用且需要重用时,首选动态 我问静态SQL为什么会阻止缓存重用,他说: 显然,当变量传递给语句谓词时,可能会阻止执行计划的缓存重用,而DSQL将允许在存储过程中重用缓存 例如:在SQL Server中,动态SQL比静态SQL性能更好吗?,sql,sql-server,Sql,Sql Server,我的一位同事声称,在许多情况下,动态SQL的执行速度比静态SQL快,所以我经常看到到处都是DSQL。除了明显的缺点,比如在运行之前无法检测到错误,而且更难阅读,这是否准确?当我问他为什么一直使用DSQL时,他说: 当静态不会阻止缓存重用时,首选静态;当静态会阻止缓存重用且需要重用时,首选动态 我问静态SQL为什么会阻止缓存重用,他说: 显然,当变量传递给语句谓词时,可能会阻止执行计划的缓存重用,而DSQL将允许在存储过程中重用缓存 例如: select * from mytable where
select * from mytable where myvar = @myvar
我不是SQL Server执行计划方面的专家,但这在我看来似乎不合理。为什么引擎会在存储过程中的DSQL语句中保留统计信息,而不是静态SQL语句?动态SQL的优点是每次运行查询时都会重新编译查询。这样做的好处是,执行计划可以利用表上最新的统计信息和任何参数的值 除了更具可读性之外,静态SQL还有一个优点,即它不需要重新编译—为运行查询节省了一个步骤,如果将解析->编译->执行计算在内,实际上是两个步骤。这可能是好事,也可能不是好事 可以使用with recompile选项强制静态计划重新编译
有时,您需要使用动态SQL。不过,一般来说,在依赖动态SQL之前,我会使用编译器提示和其他方法来管理性能。从SQL server的角度来看,我认为不应该过多地使用动态SQL。 问题可能包括: 内存中的表将以只读方式传递 将每个值连接起来后,查询将进行重新编译。 执行计划将使用表统计信息和其他数据库信息,但您是否需要重新编译执行计划。如果您觉得自己比SQL Server引擎更了解,可以修改查询以使用循环联接、哈希联接或合并联接。否则,只需按照预期的方式编写过程,并传递参数
在我看来,不要使用动态查询……而是使用每个可更改的值都作为参数传递的过程,并且没有硬编码。创建适当且较少的索引和触发器来处理数据。因此,您还可以轻松地直接使用内存表变量和内存表功能,否则内存表变量将以只读形式传递给动态查询。您需要显示与select*from mytable等效的DSQL,其中myvar=@myvar,因为一种方法是将值作为字符串的一部分放在那里,因此,删除该参数。因此,是的,您避免了参数嗅探,代价是对@myvar.Performance wise的每个可能值都有一个查询计划,尝试一下,获取静态版本的执行计划,并将其与动态版本进行比较。就编码而言,这听起来像是一场噩梦。您的同事所指的参数嗅探只是有时,我甚至很少会说,是一个问题-谷歌it。告诉您的同事阅读有关OPTIONRECOMPILE功能的文档。此外,与运行时相比,在编写时,双方都应该阅读和。更具可读性,并检查语法错误和缺少的对象。动态SQL的优点是每次运行查询时都会重新编译查询。这种说法根本不正确。编译和重新编译不依赖于动态或静态生成的查询文本。已知事实构成了我在SQL中的观点……如果您尝试使用带有内存表变量的动态查询,您就会知道。这些数据以只读方式传递,然后将更改传输到主表。此外,还有重新编译步骤。