Sql server 2008 运行缓慢的查询,CF 9&;MSSQL 2008;腐败的执行计划?
我多年来一直在研究Coldfusion/MS SQL,这是我见过的最奇怪的问题之一。问题本身已经解决了,但我真的不明白发生了什么;这个问题试图弄清楚可能的原因 问题 在一个稳定的生产环境中,没有明显的原因,一个查询在1000-1500毫秒左右开始返回(大约比平常慢10倍)。我能够将其与此隔离:Sql server 2008 运行缓慢的查询,CF 9&;MSSQL 2008;腐败的执行计划?,sql-server-2008,coldfusion,coldfusion-9,Sql Server 2008,Coldfusion,Coldfusion 9,我多年来一直在研究Coldfusion/MS SQL,这是我见过的最奇怪的问题之一。问题本身已经解决了,但我真的不明白发生了什么;这个问题试图弄清楚可能的原因 问题 在一个稳定的生产环境中,没有明显的原因,一个查询在1000-1500毫秒左右开始返回(大约比平常慢10倍)。我能够将其与此隔离: <cfquery datasource="#ds#" name="query"> select 1 from eLearning.v_courseCompletion cc
<cfquery datasource="#ds#" name="query">
select 1
from eLearning.v_courseCompletion cc
where
cc.memberIncId = <cfqueryparam value="3" cfsqltype="cf_sql_integer"> and
cc.courseId = <cfqueryparam value="25" cfsqltype="cf_sql_integer"> and
cc.currentCourseCompleted = 1
</cfquery>
选择1
来自eLearning.v_课程完成cc
哪里
cc.memberIncId=和
cc.courseId=和
cc.currentCourseCompleted=1
奇怪的是,在一个循环中,即使只有一次迭代,这种行为也会加剧,如本例所示:
<cfloop from="1" to="1" index="i">
<cfquery datasource="#ds#" name="query">
select 1
from eLearning.v_courseCompletion cc
where
cc.memberIncId = <cfqueryparam value="3" cfsqltype="cf_sql_integer"> and
cc.courseId = <cfqueryparam value="25" cfsqltype="cf_sql_integer"> and
cc.currentCourseCompleted = 1
</cfquery>
</cfloop>
选择1
来自eLearning.v_课程完成cc
哪里
cc.memberIncId=和
cc.courseId=和
cc.currentCourseCompleted=1
这应该和上面完全一样,对吗?该循环应该没有效果,但相反,该测试运行速度大约慢10倍,在7000-16000毫秒之间返回。这就是检测问题的方式;查询(隐藏在对象方法中)是从循环体调用的,如果循环迭代次数超过5或6次,请求将超时
对我来说,这表明Coldfusion方面存在问题,但重启服务,或者说重启机器,什么也没做
同时,一旦隔离,我注意到对查询本身进行任何更改都会使性能恢复到预期水平,大约150-190毫秒。例如:
- 更改所选字段(即
)选择*
- 删除表别名(
)cc
- 用内联值替换
- 删除任何条件
DBCC FREEPROCCACHE
。这立即解决了问题。太好了,问题解决了
问题
但从那以后,我做了更多的研究,大家一致认为执行计划“不会被破坏”。存储过程中可能会出现一些问题,但我这里没有使用任何sp。我们正在从一个相当复杂的视图(eLearning.v_courseCompletion
)中选择嵌套联接。这就是问题所在吗
基本上,这里到底发生了什么?我如何阻止它再次发生
。。CF中的循环连接到底是什么
版本
- Coldfusion 9.0.2.282541(64位)
- SQL Server Express 10.50.4297(64位)
- 两台服务器都是Win Server 2008 R2数据中心(64位)
StackOverflow很好地证明了这一点,如果一个特定的超级用户在创建查询统计数据之前将其数百万个徽章和点数加载到他们的帐户页面,那么它将搞乱其他每个只有几百点左右点数和少量徽章的用户的统计数据,让页面对他或她来说变慢。啊,太棒了,这很有道理。了解为什么在一个循环(甚至一次迭代)中运行它会对性能产生如此大的影响吗?谢谢,这个循环听起来不像是罪魁祸首。我会责怪循环提供的一些其他情况,例如索引变量或使循环看起来像是它应该受到责怪的东西。此外,您几乎总能避免在循环中运行cfquery。很少有时候这是有意义的。谢谢你的跟进,但我向你保证,在这个循环中没有任何其他因素可能(应该?)导致这一点;上面发布的代码块直接来自我的测试用例(加上前后的
getTickCount()
)。循环的索引(或项)变量根本不被查询引用,循环体中也没有其他内容。在编译到Java的循环过程中,可能出现了一些问题?如果我能重现这个问题,我会挖得更深一点。对不起,伙计,我想你可能可以孤立它,但我从来没有听说过。此外,如果您有兴趣看到在cfloop中运行查询的替代方案,发布一个问题,有人会为您提供帮助。通过重构循环来优化这个特定案例并不困难(但它会打破ORM的抽象)。如果可能的话,我更关心的是预防这类问题。谢谢