SQL2005 索引优化

来源:网络 责任编辑:栏目编辑 发表时间:2013-07-02 02:03 点击:

聚集索引 , 表中存储的数据按照索引的顺序存储 , 检索效率比普通索引高 , 但对数据新增 / 修改 / 删除的影响比较大

非聚集索引 , 不影响表中的数据存储顺序 , 检索效率比聚集索引低 , 对数据新增 / 修改 / 删除的影响很小

如何让你的 SQL 运行得更快

---- 人们在使用 SQL 时往往会陷入一个误区,即太关注于所得的结果是否正确,而忽略

了不同的实现方法之间可能存在的性能差异,这种性能差异在大型的或是复杂的数据库

环境中(如联机事务处理 OLTP 或决策支持系统 DSS )中表现得尤为明显。笔者在工作实践

中发现,不良的 SQL 往往来自于不恰当的索引设计、不充份的连接条件和不可优化的 whe

re 子句。在对它们进行适当的优化后,其运行速度有了明显地提高!下面我将从这三个

方面分别进行总结:

---- 为了更直观地说明问题,所有实例中的 SQL 运行时间均经过测试,不超过1秒的均

表示为( < 1 秒)。

---- 测试环境 --

---- 主机: HP LH II

---- 主频: 330MHZ

---- 内存: 128 兆

---- 操作系统: Operserver5.0.4

---- 数据库: Sybase11.0.3

一、不合理的索引设计

---- 例:表 record 有 620000 行,试看在不同的索引下,下面几个 SQL 的运行情况:

---- 1. 在 date 上建有一非个群集索引

select count(*) from record where date >

'19991201' and date < '19991214'and amount >

2000 (25 秒 )

select date,sum(amount) from record group by date

(55 秒 )

select count(*) from record where date >

'19990901' and place in ('BJ','SH') (27 秒 )

---- 分析:

----date 上有大量的重复值,在非群集索引下,数据在物理上随机存放在数据页上,在

范围查找时,必须执行一次表扫描才能找到这一范围内的全部行。

---- 2. 在 date 上的一个群集索引

select count(*) from record where date >

'19991201' and date < '19991214' and amount >

2000 ( 14 秒)

select date,sum(amount) from record group by date

( 28 秒)

select count(*) from record where date >

'19990901' and place in ('BJ','SH') ( 14 秒)

---- 分析:

---- 在群集索引下,数据在物理上按顺序在数据页上,重复值也排列在一起,因而在范

围查找时,可以先找到这个范围的起末点,且只在这个范围内扫描数据页,避免了大范

围扫描,提高了查询速度。

---- 3. 在 place , date , amount 上的组合索引

select count(*) from record where date >

'19991201' and date < '19991214' and amount >

2000 ( 26 秒)

select date,sum(amount) from record group by date

( 27 秒)

select count(*) from record where date >

'19990901' and place in ('BJ', 'SH') ( < 1 秒)

---- 分析:

---- 这是一个不很合理的组合索引,因为它的前导列是 place ,第一和第二条 SQL 没有引

用 place ,因此也没有利用上索引;第三个 SQL 使用了 place ,且引用的所有列都包含在组

合索引中,形成了索引覆盖,所以它的速度是非常快的。

---- 4. 在 date , place , amount 上的组合索引

select count(*) from record where date >

'19991201' and date < '19991214' and amount >

2000(< 1 秒 )

select date,sum(amount) from record group by date

( 11 秒)

select count(*) from record where date >

'19990901' and place in ('BJ','SH') ( < 1 秒)

---- 分析:

---- 这是一个合理的组合索引。它将 date 作为前导列,使每个 SQL 都可以利用索引,并

且在第一和第三个 SQL 中形成了索引覆盖,因而性能达到了最优。

---- 5. 总结:

---- 缺省情况下建立的索引是非群集索引,但有时它并不是最佳的;合理的索引设计要

建立在对各种查询的分析和预测上。一般来说:

---- ① . 有大量重复值、且经常有范围查询

( between, >,< , >=,< = )和 order by

、 group by 发生的列,可考虑建立群集索引;

---- ② . 经常同时存取多列,且每列都含有重复值可考虑建立组合索引;

---- ③ . 组

    相关新闻>>

      发表评论
      请自觉遵守互联网相关的政策法规,严禁发布色情、暴力、反动的言论。
      用户名: 验证码:点击我更换图片
      最新评论 更多>>

      推荐热点

      • sql常见面试题
      • SQL SERVER 2005性能之跟踪
      • SQL编程(一)
      • LINUX上RMAN自动备份脚本
      • sql server面试题
      • 如何将多个SQL查询统计结果一次显示出来
      • 浅谈SQL Server中的事务日志(三)----在简单恢复模式下日志的角色
      • sql server 列转行
      • SQL小技巧系列 --- 行转列合并
      网站首页 - 友情链接 - 网站地图 - TAG标签 - RSS订阅 - 内容搜索
      Copyright © 2008-2015 计算机技术学习交流网. 版权所有

      豫ICP备11007008号-1