SQL语句优化 (一) (52)

优化SQL语句的一般步骤

1 通过show status命令了解各种SQL的执行频率。

格式:mysql> show [session|global]status;

其中:session(默认)表示当前连接,

global表示自数据库启动至今

mysql>show status;

mysql>show global status;

mysql>show status like ‘Com_%’;

mysql>show global status like ‘Com_%’;

参数说明:

Com_XXX表示每个XXX语句执行的次数如:

Com_select 执行select操作的次数,一次查询只累计加1

Com_update 执行update操作的次数

Com_insert 执行insert操作的次数,对批量插入只算一次。

Com_delete 执行delete操作的次数

只针对于InnoDB存储引擎的。

InnoDB_rows_read 执行select操作的次数

InnoDB_rows_updated 执行update操作的次数

InnoDB_rows_inserted 执行insert操作的次数

InnoDB_rows_deleted 执行delete操作的次数

其他:

connections 连接mysql的数量

Uptime 服务器已经工作的秒数

Slow_queries:慢查询的次数

2 定位执行效率较低的SQL语句

1)explain select * from table  where id=1000;

2)desc select * from table where id=1000;

3 通过EXPLAIN分析较低效SQL的执行计划

mysql> explain select count(*) from stu where name like "a%"\G
*************************** 1. row ***************************
           id: 1
  select_type: SIMPLE
        table: stu
         type: range
possible_keys: name,ind_stu_name
          key: name
      key_len: 50
          ref: NULL
         rows: 8
        Extra: Using where; Using
index
1 row in set (0.00 sec)

每一列的简单解释

id: 1

select_type: SIMPLE 表示select的类型,常见的取值有SIMPLE()简单表,即不使用表连接或者子查询)、PRIMARY(主查询,即外层的查询)、UNION(UNION中的第二个或者后面的查询语句)、SUBQUERY(子查询中的第一个SESECT)等

table: stu   输出结果集的表

type: range  表示表的连接类型,性能有好到差:system(表仅一行)、const(只一行匹配)、eq_ref(对于前面的每一行使用主键和唯一)、ref(同eq_ref,但没有使用主键和唯一)、ref_or_null(同前面对null查询)、index_merge(索引合并优化)、unique_subquery(主键子查询)、index_subquery(非主键子查询)、range(表单中的范围查询)、index(都通过查询索引来得到数据)、all(通过全表扫描得到的数据)

possible_keys: name,ind_stu_name  表查询时可能使用的索引。

key: name   表示实际使用的索引。

key_len: 50  索引字段的长度

ref: NULL

rows: 8   扫描行的数量

Extra: Using where; Using index 执行情况的说明和描述

索引问题

索引是数据库优化中最常见也是最重要的手段之一,通过索引通常可以帮助用户解决大多数的SQL性能问题。

索引的存储分类

MyISAM存储引擎的表的数据和索引是自动分开存储的,各自是独一的一个文件;InnoDB存储引擎的表的数据和索引是存储在同一个表空间里面,但可以有多个文件组成。

MySQL目前不支持函数索引,但是能对列的前面某一部分进行索引,例如name字段,可以只取name的前4个字符进行索引,这个特性可以大大缩小索引文件的大小,用户在设计表结构的时候也可以对文本列根据此特性进行灵活设计。

mysql>create index ind_company2_name on company2(name(4));
  其中company表名 ind_company2_name索引名

MySQL如何使用索引

索引用于快速找出在某个列中有一特定值的行。对相关列使用索引是提高SELECT操作性能的最佳途径。

1、使用索引

(1)对于创建的多列索引,只要查询的条件中用到最左边的列,索引一般就会被使用。如下创建一个复合索引。

mysql>create index ind_sales2_com_mon onsales2(company_id,moneys);

然后按company_id进行查询,发现使用到了复合索引

mysql>explain select * from sales2 where company_id=2006\G

使用下面的查询就没有使用到复合索引。

mysql>explain select * from sales2 where moneys=1\G

(2) 使用like的查询,后面如果是常量并且只有%号不在第一个字符,索引才可能会被使用,如下:

mysql> explain select * from company2 where name like "%3"\G
*************************** 1. row ***************************
           id: 1
  select_type: SIMPLE
        table: company2
         type: ALL
possible_keys: NULL
          key: NULL
      key_len: NULL
          ref: NULL
         rows: 1000
        Extra: Using where
1 row in set (0.00 sec)

如下这个使用到了索引,而下面例子能够使用索引,区别就在于“%”的位置不同,上面的例子是吧“%”放在了第一位,而下面的例子则没有

mysql> explain select * from company2 where name like “3%"\G
*************************** 1. row ***************************
           id: 1
  select_type: SIMPLE
        table: company2
         type: range
possible_keys: ind_company2_name
          key:
ind_company2_name
      key_len: 11
          ref: NULL
         rows: 103
        Extra: Using where
1 row in set (0.00 sec)

(3)如果对大的文本进行搜索,使用全文索引而不使用 like“%...%”.

(4)如果列名是索引,使用column_name is null将使用索引。如下

mysql> explain select * from company2 where name is null\G
*************************** 1. row ***************************
           id: 1
  select_type: SIMPLE
        table: company2
         type: ref
possible_keys: ind_company2_name
          key:
ind_company2_name
      key_len: 11
          ref: const
         rows: 1
        Extra: Using where
1 row in set (0.00 sec)

2、存在索引但不使用索引

(1)如果MySQL估计使用索引比全表扫描更慢,则不使用索引。例如如果列key_part1均匀分布在1到100之间,查询时使用索引就不是很好

mysql>select * from table_name where key_part1>1 and key_part<90;

(2)如果使用MEMORY/HEAP表并且where条件中不使用“=”进行索引列,那么不会用到索引。Heap表只有在“=”的条件下会使用索引。

(3)用or分割开的条件,如果or前的条件中的列有索引,而后面的列中没有索引,那么涉及的索引都不会被用到。

mysql>show index from sales\G


 *************************** 1. row ***************************       
    … …
   key_name: ind_sales_year
   seq_in_index:1
   Column_name: year
    … …

时间: 2024-10-08 03:20:40

SQL语句优化 (一) (52)的相关文章

SQL语句优化技术分析

摘自  http://www.cnblogs.com/wxj1020/archive/2008/04/27/1173638.html 最近几周一直在进行数据库培训,老师精湛的技术和生动的讲解使我受益匪浅.为了让更多的新手受益,我抽空把SQL语句优化部分进行了整理,希望大家一起进步. 一.操作符优化 1.IN 操作符 用IN写出来的SQL的优点是比较容易写及清晰易懂,这比较适合现代软件开发的风格.但是用IN的SQL性能总是比较低的,从Oracle执行的步骤来分析用IN的SQL与不用IN的SQL有以

Mysql性能优化----SQL语句优化、索引优化、数据库结构优化、系统配置优化、服务器硬件优化

一.SQL语句优化 1-1.MySQL慢日志 1).慢日志开启方式和存储格式 如何发现有问题的SQL? 使用Mysql慢日志对有效率问题的SQL进行监控 前期准备 mysql> show variables like '%log_queri%'; +-------------------------------+-------+ | Variable_name | Value | +-------------------------------+-------+ | log_queries_no

MySQL之SQL语句优化

一 SQL语句优化的一般步骤: 1 通过show status命令了解各种SQL语句的执行频率 mysql> show status;                #show status:显示服务器状态信息 +-----------------------------------------------+-------------+ | Variable_name                                 | Value       | +---------------

小贝_mysql sql语句优化过程

sql语句优化 一.SQL优化的一般步骤 (1).通过show status命令了解各种SQL的执行频率. (2).定位执行效率较低的SQL语句-(重点select) (3).通过explain分析低效率的SQL语句的执行情况 (4).确定问题并采取相应的优化措施 (1) 通过showstatus命令了解各种SQL的执行频率 MySQL客户端连接成功后,通过使用show[session|global] status 命令可以提供服务器状态信息.其中的session来表示当前的连接的统计结果,gl

Oracle SQL语句优化34条

非常好用的SQL语句优化34条 1)选择最有效率的表名顺序(只在基于规则的优化器中有效): ORACLE 的解析器按照从右到左的顺序处理FROM子句中的表名,FROM子句中写在最后的表(基础表 driving table)将被最先处理,在FROM子句中包含多个表的情况下,你必须选择记录条数最少的表作为基 础表.如果有3个以上的表连接查询, 那就需要选择交叉表(intersection table)作为基础表, 交叉表是指那个被其他表所引用的表. (2) WHERE子句中的连接顺序.: ORACL

Oracle Sql语句优化

1.最高效的删除重复记录方法 (因为使用了ROWID)   例子:  DELETE FROM  EMP E  WHERE  E.ROWID > (SELECT MIN(X.ROWID) FROM  EMP X  WHERE  X.EMP_NO = E.EMP_NO); 2.在含有子查询的 SQL 语句中 , 要特别注意减少对表的查询   例子:  SELECT TAB_NAME FROM TABLES WHERE (TAB_NAME,DB_VER) = (SELECT TAB_NAME,DB_V

对SQL语句优化的思考

软件在研发的过程中自始至终都在留意着系统的可扩展性,但与此同时也在关注着系统的性能,SQL语句作为系统性能的一环不容忽视,从今天开始结合开发的经验,谈一下我对SQL语句优化的理解和认知: 1.在联合查询语句中做到小表驱动大表: 联合查询是常用到的一种查询方式,左连接.右连接.内连接等等时不时地被应用在查询语句中,然而在这一过程中如果能判明各表的数据量,那就再好不过了,在这种情况下from后面应该紧跟数据量小的表,为什么?呵呵呵,比如a表有1000条数据,b表有20条数据,使用左连接进行联合查询如

Oracle大数据SQL语句优化

1.对查询进行优化,应尽量避免全表扫描,首先应考虑在 where 及 order by 涉及的列上建立索引. 2.应尽量避免在 where 子句中对字段进行 null 值判断,否则将导致引擎放弃使用索引而进行全表扫描, 如: select id from t where num is null    可以在num上设置默认值0,确保表中num列没有null值,然后这样查询: select id from t where num=0 3.应尽量避免在 where 子句中使用!=或<>操作符,否则

提高系统性能——对SQL语句优化的思考

软件在研发的过程中自始至终都在留意着系统的可扩展性.但与此同一时候也在关注着系统的性能,SQL语句作为系统性能的一环不容忽视.从今天開始结合开发的经验,谈一下我对SQL语句优化的理解和认知: 1.在联合查询语句中做到小表驱动大表: 联合查询是经常使用到的一种查询方式,左连接.右连接.内连接等等时不时地被应用在查询语句中,然而在这一过程中假设能判明各表的数据量,那就再好只是了,在这样的情况下from后面应该紧跟数据量小的表.为什么?呵呵呵,比方a表有1000条数据,b表有20条数据.使用左连接进行

SQL系列 - SQL语句优化个人总结

关于SQL语句优化方法 有些是通用的(如避免Select *): 有些不同的数据库管理系统有所区别(如Where子句顺序): 然后必须根据实际环境进行调优,因为即使是相同的数据库和表,在数据量或其他环境变化之后,SQL效率可能是不同的.所以,优化不是一蹴而就的. 一些总结 下面是我在工作中,主要是Oracle环境下一些常用的SQL语句优化方法,仅供参考.当然,后续可以再深入研究下SQL执行计划.索引等. 指明需要的列 Selcet中每少提取一个字段,数据的提取速度就会有相应的提升.提升的速度还要