脚本优化

1.        Select 查询字段最好不要用“*”,严格表明查询字段名称,查询仅仅返回需要的行和列;

2.        避免使用NOT IN,可以用LEFT OUTER JOIN代替它;

3.        注意一些or子句和union子句之间的替换

4.        Union Union All的区别;

Union 会把两个结果集排序,并且除去重复的元素(效率差,轻易不要用);

Union All仅仅是把两个结果集合并,没有排序,也不去除重复元素(效率好)

5.        注意表之间连接的数据类型,避免不同类型数据之间的连接。

6.        注意存储过程中参数和数据类型的关系。

7.      尽量使用exists代替select count(1)来判断是否存在记录count函数只有在统计表中所有行数时使用而且count(1)count(*)更有效率。

8.        不要在where子句中进行函数、算术运算或其他表达式运算

否则系统将可能无法正确使用索引;注意where字句写法,必须考虑语句顺序,应该根据索引顺序、范围大小来确定条件子句的前后顺序,尽可能的让字段顺序与索引顺序相一致,范围从大到小。

9.        重复访问同一表,考虑临时表存储

尽量避免反复访问同一张或几张表,尤其是数据量较大的表,可以考虑先根据条件提取数据到临时表中,然后再做连接。

10.     SET NOCOUNT ON 时,也更新 @@ROWCOUNT 函数。

@@ROWCOUNT是返回受上一语句影响的行数包括找到记录的数目、删除的行数、更新的记录数等不要认为是返回查找的记录数目而且@@ROWCOUNT要紧跟需要判断语句否则@@ROWCOUNT将返回0
   
使用错误处理程序,用来检查 @@ERROR 系统函数的 T-SQL 语句 (IF) 实际上在进程中清除了 @@ERROR 值,无法再捕获除零之外的任何值,必须使用 SET SELECT 立即捕获错误代码。

11.     注意insertupdate操作的数据量,防止与其他应用冲突。

如果数据量超过一定的数据页面,系统将会进行锁升级,页级锁会升级成表级锁。

12.     避免使用游标

尽量避免使用游标,游标的效率较差,因为游标基本上是强制优化器执行固定的计划,并且逐行操作产生大量的开销;如果使用了游标,就要尽量避免在游标循环中再进行表连接的操作。

13.      sp_executesql动态执行脚本

如果需要使用动态SQLsp_executesql更具优势,因为它提供了输入输出接口,并且更有可能重用执行计划,因为你可以更容易的生成被重复调用的查询字符串。注意有一点声明的参数类型尽量和查询关键字字段类型一致,否则可能导致低的查询效率。

实例代码:

     declare @user varchar(1000), @cQQNum varchar(20),

@moTable varchar(20)

select @moTable = 'UserInf'

declare @sql nvarchar(4000)

--定义变量,注意类型

set @sql='select top 1 @user = cUserName,@cQQNum=cQQNum from '+@moTable 

--执行@sql中的语句

exec sp_executesql @sql,N'@user varchar(1000) out,@cQQNum varchar(20) out',@user out,@cQQNum out --和调用存储过程差不多,指定输出参数值

select @user, @cQQNum

 

14.     临时表的使用

临时表和表变量被物理的保存在tempdb中,尽量少的使用临时表,因为大量使用临时表可能使tempdb成为瓶颈。可以使用表表达式,包括派生表、CTE、视图和内联表值UDF

补充:CTESQL Server 2005的一项强大而灵活的功能。它使得SQL Server的可读性更强,更易于管理,降低了查询的复杂程度。执行递归查询是CTE最重要也是最强大的功能。

1. 尽量少的使用distinctorder bygroup byhavingjoin,因为这些语句会加重tempdb的负担。
2. 避免
频繁创建和删除临时表,减少系统表资源的消耗。
3. 在新建临时表时,如果一次性插入数据量很大,那么可以
使用select into代替create table,避免log,提高速度;如果数据量不大,为了缓和系统表的资源,建议先create table,然后insert
4. 如果
临时表的数据量较大,需要建立索引,那么应该将创建临时表和建立索引的过程放在单独一个子存储过程中,这样才能保证系统能够很好的使用到该临时表的索引。
5. 如果使用到了临时表,在存储过程的最后
务必将所有的临时表显式删除,先truncate table,然后drop table,这样可以避免系统表的较长时间锁定。
6. 慎用大的临时表与其他大表的连接查询和修改,减低系统表负担,因为这种操作会在一条语句中多次使用tempdb的系统表。

 

15.     视图的使用

尽量少用视图,它的效率低。对视图操作比直接对表操作慢,可以用stored procedure来代替她。特别的是不要用视图嵌套,嵌套视图增加了寻找原始资料的难度。我们看视图的本质:它是存放在服务器上的被优化好了的已经产生了查询规划的SQL。对单个表检索数据时,不要使用指向多个表的视图,直接从表检索或者仅仅包含这个表的视图上读,否则增加了不必要的开销,查询受到干扰.为了加快视图的查询,MsSQL增加了视图索引的功能。

 

16.     当在TSQL中引用对象时,建议使用对象的架构名称限定。

(使用dbo.sysdatabases代替sysdatabases)未指定架构可能会导致混淆和意义不明确,还有一个重要原因,当很多连接同时运行同一个存储过程时,如果未指定架构名称,这些连接可能会因为要获取编译锁(compile lock)而互相阻塞。

 

17.     跨库操作表时

如果用到其他库的TableView可以在当前库中建立View来实现跨库操作最好不要直接使用databse.shema.table_name因为sp_depends显示有关数据库对象依赖关系的信息不能显示出该SP所使用的跨库tableview不方便校验。

--执行下面的存储过程显示数据库中依赖于表的数据库对象

EXEC sp_depends @objname = N'user';

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值