SQLServer性能优化一则小实例(2010-07-22)
2010-07-22 22:30
155 查看
今天下午优化了一个存储过程,通过sys.dm_exec_query_stats和sys.dm_exec_sql_text() 定位到的,发现运行次数虽然很少,但是每次却长达上千万毫秒的cpu消耗,但实际执行虽然时间比较久,却也不过几十分钟而已,不知道是不是SQLServer系统性能视图的缺陷。
既然有问题那就找吧
这是一个存储过程,类似于
create procedure sp_exec_task
as
declare cursor cur_test for select * from tableA
begin
open cur_test
fetch cur_test into ...
WHILE @@FETCH_STATUS=0
BEGIN
if true
update tableB where id=tableA.id and other_cond
else
update tableB where id=tableA.id and other_cond
if true
update tableC where id=tableA.id and other_cond
else
update tableC where id=tableA.id and other_cond
fetch cur_test into ...
end
CLOSE cur_test
DEALLOCATE cur_test
end
怎么分析呢?
1、开始的时候是让游标空循环,发现一共1万多条记录,空循环时间基本为0
2、再次把所有的DML语句转化为SELECT,并记录每个步骤的运行时间和一次完整游标的循环时间
最后循环中变为
BEGIN
print 'step 1'+convert(varchar,109,getdate()
select * from tableB where id=tableA.id and other_cond
print 'step 1'+convert(varchar,109,getdate()
select * from tableC where id=tableA.id and other_cond
END
通过上百次的循环测试,发现每次循环大概需要60毫秒,100次的花就是6秒,10000次可不就是10分钟
3、检查了一下游标循环中用的表和where条件,发现选择性不错,就添加索引,再次安装上面的办法进行测试
这次是单次循环0~1毫秒,100次大概是1秒,10000次还是需要1分多钟的
4、1分多钟是可以忍受的,干脆直接测完吧,运行过程中,不断发现内存消耗极大,很快居然耗光了内存
5、添加了SET NOCOUNT ON之类的,运行后还是内存暴增
6、后来思考了一下是不是select * from tableB的不断刷新导致的,直接修改为
select top 1 @tt=tt from tableB where id=tableA.id and other_cond
这样就不会持续刷新屏幕了
7、运行后,果然只需要短短的4秒钟。
总结:
其实在数据库中与性能相关的,无论是耗cpu还是耗内存还是耗硬盘还是锁的问题,分析到最后,95%以上都与SQL和索引相关
首先要找到问题,才能谈到分析问题,分析问题就在于多实践,而实践在于尽量屏蔽与问题无关的外界因素。
既然有问题那就找吧
这是一个存储过程,类似于
create procedure sp_exec_task
as
declare cursor cur_test for select * from tableA
begin
open cur_test
fetch cur_test into ...
WHILE @@FETCH_STATUS=0
BEGIN
if true
update tableB where id=tableA.id and other_cond
else
update tableB where id=tableA.id and other_cond
if true
update tableC where id=tableA.id and other_cond
else
update tableC where id=tableA.id and other_cond
fetch cur_test into ...
end
CLOSE cur_test
DEALLOCATE cur_test
end
怎么分析呢?
1、开始的时候是让游标空循环,发现一共1万多条记录,空循环时间基本为0
2、再次把所有的DML语句转化为SELECT,并记录每个步骤的运行时间和一次完整游标的循环时间
最后循环中变为
BEGIN
print 'step 1'+convert(varchar,109,getdate()
select * from tableB where id=tableA.id and other_cond
print 'step 1'+convert(varchar,109,getdate()
select * from tableC where id=tableA.id and other_cond
END
通过上百次的循环测试,发现每次循环大概需要60毫秒,100次的花就是6秒,10000次可不就是10分钟
3、检查了一下游标循环中用的表和where条件,发现选择性不错,就添加索引,再次安装上面的办法进行测试
这次是单次循环0~1毫秒,100次大概是1秒,10000次还是需要1分多钟的
4、1分多钟是可以忍受的,干脆直接测完吧,运行过程中,不断发现内存消耗极大,很快居然耗光了内存
5、添加了SET NOCOUNT ON之类的,运行后还是内存暴增
6、后来思考了一下是不是select * from tableB的不断刷新导致的,直接修改为
select top 1 @tt=tt from tableB where id=tableA.id and other_cond
这样就不会持续刷新屏幕了
7、运行后,果然只需要短短的4秒钟。
总结:
其实在数据库中与性能相关的,无论是耗cpu还是耗内存还是耗硬盘还是锁的问题,分析到最后,95%以上都与SQL和索引相关
首先要找到问题,才能谈到分析问题,分析问题就在于多实践,而实践在于尽量屏蔽与问题无关的外界因素。
相关文章推荐
- SQLServer性能优化一则小实例(2010-07-22)
- SQLServer性能优化一则小实例(2010-07-21)
- SQLServer性能优化一则小实例(2010-07-21)
- SQLServer性能优化一则小实例
- Android性能优化——实例
- 04.SQLServer性能优化之---读写分离&数据同步
- 企业应用网站性能优化实例分析_SEO的关键
- SQLServer性能优化
- 性能优化——统计信息——SQLServer自动更新和自动创建统计信息选项
- 企业应用网站性能优化实例分析
- 面试MCS PFE电话面试 sqlserver性能优化想到的
- SQLServer分页功能性能优化
- MySQL查询性能优化一则
- SQLServer性能优化之 nolock,大幅提升数据库查询性能
- oracle实例的内存(SGA和PGA)调整,优化数据库性能
- webpack实例与前端性能优化
- SQLServer------Sql Server性能优化辅助指标SET STATISTICS TIME ON和SET STATISTICS IO ON
- 01.SQLServer性能优化之----强大的文件组----分盘存储
- Java程序性能和速度优化实例
- SQLServer性能优化之活用临时表