禁止在数据库做复杂运算
·XML解析
·字符串相似性比较
·字符串搜索(charindex)
·……
·复杂运算在程序端完成
禁止使用SELECT *
·减少内存消耗和网络带宽
·给查询优化器有机会从索引读取所需要的列
·表结构变化时容易引起查询出错
·只返回必要的列
设置查询条件,只返回必要的记录
在SELECT语句中使用WHERE子句,设置查询条件,只返回必要的记录。
减少内存消耗和网络带宽
查询的模糊匹配
尽量避免在一个复杂查询里面使用LIKE ’%parm1%’——红色标识位置的百分号会导致相关列的索引无法使用,最好不要用。LIKE ‘parm1%’这个用到索引。
解决方法:
A、 修改前台程序——把查询条件由原来的文本输入改成下拉列表,这样就可以直接用等于来关联了。
B、 直接修改后台——根据查询条件,先查出符合条件的值,并把相关记录保存在一个临时表中,然后再用临时表去做复杂关联。
禁止在索引列上使用函数或计算
在WHERE子句中,如果是索引是函数的一部分,优化器将不再使用索引而使用全表扫描。假设在字段Col1上建有一个索引,则下列场景将无法使用到索引:
ABS[Col1]=1
[Col1]+1>9
在举例说明一下
SELECTOrderID,PrintTime,PrintFlag FROM O_OrderProcess WHERECONVERT(VARCHAR(10),PrintTime,121)=’2012-07-23’
这样的话无法使用PrintTime索引,应该这样查:
SELECTOrderID,PrintTime,PrintFlag FROM O_OrderProcess WHERE PrintTime>=’2012-07-2300:00:00’ AND PrintTime <’2012-07-24 00:00:00’
下列场景可以使用到索引
[Col1]=3.14
[Col1]>100
[Col1] BETWEEN 0 AND 99
[Col1] LIKE ‘abc%’
[Col1] IN (2,3,7)
禁止使用游标,内存和锁资源消耗非常大
限制JOIN个数
·单个SQL语句的表JOIN个数不超过5个
·过多的JOIN个数会导致查询分析器走错执行计划
·过多JOIN在编制执行计划时消耗很大
限制IN子句中条件个数,限制在100个以内
使用UNION ALL替换UNION
UNION会对SQL结果集去重排序,增加CPU、内存等消耗,通常速度上会慢。若UNION ALL能满足要求的话,务必使用UNION
尽量避免使用OR运算符
对于OR运算符,通常会使用全表扫面,考虑分解成多个查询用UNION/UNION ALL来实现,这里要确认查询能走到索引并返回较少的结果集
慎用Distinct关键字
·使用Distinct关键字过滤掉重复的记录会浪费查询的时间和系统资源。
·使用Group By 替换Distinct
用Between代替In
在WHERE子句中,有时适用Between关键字比使用In关键字要快,因为In关键字对其后门的集合中的每个元素进行比较操作。
如果必须使用In关键字,则可将频繁使用的值放在集合的前面,从而减少比较的次数。
限制嵌套查询
避免使用耗费资源的操作
创建临时表
部分UPDATE、SELECT语句写得很复杂(经常嵌套多级子查询)——可以考虑适当拆分几步,先生成一些临时数据表,再进行关联操作。
查询语句如果需要,可以在临时表上创建索引。
尽量避免大事务操作
·只在数据需要更新时开始事务,减少资源锁持有时间
·增加事务异常捕获预处理机制