开发人员是很少注意SQL对数据库性能影响的重要性的,大多程序员都会认为SQL是比较简单的,需要的时候查查手册就可以了,很少有深究的。

这样的观念对大型系统的开发是致命的,需要纠正这样的观念。

造成这样的原因,可能有如下几种:

1,对数据库性能的研究,成果不是显而易见,对程序员的成就感激励不足,因为开发环境中的数据很少,数据库性能好坏体现不出来,好的sql和差的sql体现不出差别,所以,更多的人选择的是写出来就可以了,没有想到过性能。没有吃过这方面的亏,没有深刻的教训,人总是要有了教训才会重视,而以教训作为学习方法其实是很高成本的。

2,程序员更重视能写多少功能,会多少语言,对于一些不是显而易见和不好衡量的能力是不够重视的。

今天客户的一套系统因为一段sql没有考虑性能问题,导致数据在几万条数据的情况下,竟然也出现了巨大的性能开销,导致系统瘫痪无法使用的状况,所以,觉得有必要将一些心得写出来与大家共享。

索引是非常重要的,但是很多人是不重视的。

我总是不厌其烦的向很多开发人员介绍索引的重要性,但是,很多时候都可以从他们脸上看出来那种不以为然,但我还是在不厌其烦的向他们讲解,因为索引能否正确使用对系统的性能太重要了。

我觉得几个重要而简单的概念应该是必须掌握的:

a.聚集索引和非聚集索引,各应该用在什么场合

b.什么样的语句会使用索引,什么样的语句将不使用索引

c.应该在什么样的字段上面建立索引

d.复合索引的使用特点

一些具体的规则,如果不能理解,死记住也会获益

1,经常用来做联接的字段上面加索引

2,经常用来做条件的字段上面加索引

3,坚决避免在条件中使用否定意义的计算符,如:

select * from table1 where column1 not in (select column2 from table2)

select * from table1 where column1 not exists (select column2 from table2)

select * from table1 where id <> 100

4,聚集索引能对范围查询的性能产生巨大的提升,一定要善加利用,但是如果使用不当,也会带来巨大的性能损失

如你可以将一个订单表的订单日期加上聚集索引,订单日期是递增的,这样你按照日期范围查询时,你将获得最高的性能

select * from 客户订单 where 订单日期 between '2005-1-1' and '2005-1-31'  --是范围的查询

但是你把客户编号作为聚集索引,将不会带来重大的性能提升,反而会有负效果,因为订单的顺序客户编号是非顺序的,这样由于聚集索引需要重新排列物理磁盘,这样将会给数据写入带来巨大的开销

5,不要在生成顺序不规则的字段上面加聚集索引,应该选择能够按照递增或递减顺序生成数据的字段作为聚集索引的字段

6,坚决避免对条件字段何作为连接的字段进行运算,甚至使用函数,如:

select * from UserInfo where firstname + lastname = 'Bill Gates'

select * from UserInfo where dbo.fGetBasicSalary(UserInfo.UserId) = 2000

select * from table1 inner join table2  on table1.A + table1.B = table2.C

7,建立索引是有必要的,但不是越多越好

8,可能的话,主键多用整型值,用一个整型字段做连接,比一个字符串在大数据量的情况下性能会提高很多

9,不要把大数量的内容放到 in ()里面,如避免如下写法:

select * from table1 where column1 in (select column2 from table2) --如果此时table2的数据量比较大的情况下,性能将会非常差

其实类似的语句经常可以改写为连接的方式来实现

10,经常用来Order By的字段加上索引,也会有性能的提升

11,子查询不要出现太多,大多数能够使用外连接来替代

select *,
(select z1 from T1 where z2=T2.Id) z1,
(select z2 from T1 where z2=T2.Id) z2,
(select z3 from T1 where z2=T2.Id) z3,
from T2

这段语句肯定不是优化的,会有性能问题的,可以有如下的方式来改写

select *, T1.Z1, T1.Z2, T1.Z3

from T2 left outer join T1 on T1.Z2 = T2.ID

12,对于like的使用

推荐:select * from 用户 where 姓名 like '李%'

不推荐:select * from 用户 where 姓名 like '%白%'

建议:

写点东西算作抛砖引玉吧,希望能给一些数据库初学者一些指引和建议吧!

还有就是,如果我们的系统出现了性能的问题,多从软件的角度来考虑优化,而不是动不动就要求客户升级服务器,硬件的改善对性能的提升能力是很有限的,提高一倍,两倍都是很厉害的了,而软件的优化有时候能起到数十倍,上百倍,甚至更高的性能提升。

呼吁大家提高对数据性能的重视。

查看执行时间

declare @d datetime

  set @d=getdate()

  并在select语句后加:

  select [语句执行花费时间(毫秒)]=datediff(ms,@d,getdate())

如何写出性能好的sql的更多相关文章

  1. 写出易调试的SQL(修订版)

    h4 { background: #698B22 !important; color: #FFFFFF; font-family: "微软雅黑", "宋体", ...

  2. 写出易调试的SQL

    h4 { background: #698B22 !important; color: #FFFFFF; font-family: "微软雅黑", "宋体", ...

  3. 写出易调试的SQL—西科软件

    1.前言 上篇 写出易调试的SQL , 带来了一些讨论, 暴露了不能重用执行计划和sql注入问题, 十分感谢园友们的建议 . 经过调整后 ,将原来的SQLHelper 抓SQL 用做调试环境用, 发布 ...

  4. Mysql写出高质量的sql语句的几点建议

    CleverCode在实际的工作也写过一些低效率的sql语句.这些语句会给数据库带来非常大的压力.最基本的表现就是sql语句执行慢,后来逐渐的去优化和尝试. 总结了一些高质量的sql语句的写法.这里C ...

  5. 写出易于调试的SQL

    1.前言 相比高级语言的调试如C# , 调试SQL是件痛苦的事 . 特别是那些上千行的存储过程, 更是我等码农的噩梦. 在将上千行存储过程的SQL 分解到 C# 管理后, 也存在调试的不通畅, 如何让 ...

  6. Oracle 如何写出高效的 SQL

    转自:Oracle 如何写出高效的 SQL 要想写出高效的SQL 语句需要掌握一些基本原则,如果你违反了这些原则,一般情况下SQL 的性能将会很差. 1. 减少数据库访问次数连接数据库是非常耗时的,虽 ...

  7. 数据库性能调优——sql语句优化(转载及整理) —— 篇1

    一.问题的提出                    在应用系统开发初期,由于开发数据库数据比较少,对于查询SQL语句,复杂视图的的编写等体会不出SQL语句各种写法的性能优劣,但是如果将应用系统提交实 ...

  8. 数据库性能优化之SQL语句优化

    一.问题的提出 在应用系统开发初期,由于开发数据库数据比较少,对于查询SQL语句,复杂视图的编写等是体会不出SQL语句各种写法的性能优劣,但是如果将应用系统提交实际应用后,随着数据库中数据的增加,系统 ...

  9. 数据库性能优化之SQL语句优化(上)

    一.问题的提出 在应用系统开发初期,由于开发数据库数据比较少,对于查询SQL语句,复杂视图的编写等体会不出SQL语句各种写法的性能优劣,但是如果将应用系统提交实际应用后,随着数据库中数据的增加,系统的 ...

随机推荐

  1. css3属性整理

    浏览器内核:主流内容主要有Mozilla(熟悉的有Firefox,Flock等浏览器).WebKit(熟悉的有Safari.Chrome等浏览器).Opera(Opera浏览器).Trident(讨厌 ...

  2. static函数与普通函数

    转自http://blog.163.com/sunshine_linting/blog/static/44893323201191294825184/ 全局变量(外部变量)的说明之前再冠以static ...

  3. linux命令中 rpm –qa|grep softname的含义

    rpm –qa是列出所有rpm包后面接管道 |grep softname就是查含有softname的包名

  4. 网上图书商城项目学习笔记-036工具类之CommonUtils及日期转换器

    1.CommonUtils.java package cn.itcast.commons; import java.util.Map; import java.util.UUID; import or ...

  5. 核心思想:早胜过一切,张小龙的Foxmail居然可以卖1200万

    现在谁都可以做一个类似的软件,但是市场已经成熟了,满大街都是,也就没有人会来收购你的软件了.

  6. c# 可访问性级别

    使用访问修饰符 public.protected.internal 或 private 可以为成员指定以下声明的访问级别之一.   声明的可访问性 含义 public 访问不受限制. protecte ...

  7. Tomcat下server.xml中context介绍

    conf/Context.xml是Tomcat公用的环境配置;若在server.xml中增加<Context path="/test" docBase="D:\te ...

  8. POJ2635——The Embarrassed Cryptographer(高精度取模+筛选取素数)

    The Embarrassed Cryptographer DescriptionThe young and very promising cryptographer Odd Even has imp ...

  9. SOCKS5协议

    SOCKS5 是一个代理协议,这种协议对本身所代理的内容并不关心,可用于穿越防火墙. 例如我有一台web服务器,用户可以登陆上去查询公司的关键数据,这样的服务器我肯定是不想放到公网上让别人能随便访问, ...

  10. Android日期时间选择器实现以及自定义大小

    本文主要讲两个内容:1.如何将DatePicker和TimePicker放在一个dialog里面:2.改变他们的宽度: 问题1:其实现思路就是自定义一个Dialog,然后往里面同时放入DatePick ...