游标性能千倍之差
2010-09-28 09:41 greg_echo 阅读(634) 评论(3) 收藏 举报前几天写了一个存储过程,用于处理失败记录,处理流程大体为:

注1:从总数据表Tb_All中每次取一条数据与Tb_Fail中的数据进行比对,查看该记录成功还是失败,如果过失败则从表Tb_All中删除该记录,成功则保留该记录。
注2:Tb_Fail表中不止包含Tb_All表的记录还包括其它表记录。
注3:Tb_All数据量200万,Tb_Fail数据量20万。
处理方法一:
在一开始的处理方法中并没有对性能考虑太多,随手用了数据库游标,一条一条取记录然后比对记录,进行操作。
代码如下:
--循环表
declare @count int
select @count=count(*) from Tb_All
if (@count>0)
begin
declare @mobile varchar(21)
DECLARE table_cur CURSOR FOR
SELECT mobile FROM Tb_All
OPEN table_cur
FETCH NEXT FROM table_cur INTO @mobile
WHILE @@fetch_status = 0
BEGIN
--减少数据
if exists(select * from tb_Fail where msisdn=@mobile)
begin
delete from tb_UserScheme where us_msisdn=@mobile
end
end
FETCH NEXT FROM table_cur INTO @mobile
END
DEALLOCATE table_cur
end
等写完存储过程进行测试时,才恍然大悟,性能极为低下,每条记录都是平均10万次查询,整个表记录查询完大约要进行千亿次操作。而且从执行时间看也的确如此,大约跑了3个小时还没有跑完,实在看不下去了,就给停了。
处理方法二:
使用连接表的方式进行查询:
代码如下:
--循环表 declare @count int select @count=count(*) from tb_All if (@count>0) begin if exists(select tb_Fail.msisdn from tb_All,tb_Fail where msisdn=tb_All.mobile) begin delete tb_All from tb_Fail where tb_Fail.msisdn=tb_All.mobile end end
写完执行,耗时13秒,搞定。
此文亦水,只是给大家一个更直观的对比游标的性能的例子,希望大家多拍砖!
浙公网安备 33010602011771号