zoukankan      html  css  js  c++  java
  • 教你编写高功用的mysql语法

       来历:网海拾贝




    在使用体系启迪初期,因为启迪数据库数据对照少,对付查询SQL语句,庞年夜视图的的编写等体会不出SQL语句各类写法的功用黑白,可是假定将使用体系提交现实使用后,随着数据库中数据的添加,体系的照应速度就成为今朝体系需求处置惩罚的最重要的问题之一。体系优化中一个很重要的方面便是SQL语句的优化。对付海量数据,劣质SQL语句和优质SQL语句之间的速度不同可以到达上百倍,可见对付一一般系不是庞年夜地能完成其功用就可,而是要写出高质量的SQL语句,提高体系的可用性。

    在年夜都状况下,Oracle运用索引来更快地遍历表,优化珍视要依照界说的索引来提高功用。可是,假定在SQL语句的where子句中写的SQL代码不同理,就会形成优化器删去索引而运用全表扫描,一样普通就这种SQL语句便是所谓的劣质SQL语句。在编写SQL语句时我们应懂得优化器依照何种准绳来删除索引,这有助于写出高功用的SQL语句。

    二、SQL语句编写注重问题
    上面就某些SQL语句的where子句编写中需求注重的问题作详细先容。在这些where子句中,即便某些列存在索引,可是因为编写了劣质的SQL,体系在运转该SQL语句时也不能运用该索引,而异样运用全表扫描,这就形成了照应速度的极年夜降低。

    1. IS NULL 与 IS NOT NULL
    不能用null作索引,任何包罗null值的列都将不会被包罗在索引中。即便索引有多列多么的状况下,只需这些列中有一列含有null,该列就会从索引中拂拭。也便是说假定某列存在空值,即便对该列建索引也不会提高功用。

    任安在where子句中运用is null或is not null的语句优化器是不答应运用索引的。

    2. 联接列

    对付有联接的列,即便最后的联接值为一个静态值,优化器是不会运用索引的。我们一同来看一个例子,假定有一个职工表(employee),对付一个职工的姓和名分红两列存放(FIRST_NAME和LAST_NAME),今朝要查询一个叫比尔.克林顿(Bill Cliton)的职工。

    上面是一个给与联接查询的SQL语句,

    select * from employss
    where
    first_name||''||last_name ='Beill Cliton' 

    上面这条语句完全可以查询出能否有Bill Cliton这个员工,可是这里需求注重,体系优化器对基于last_name成立的索引没有运用。

    当给与上面这种SQL语句的编写,Oracle体系就可以给与基于last_name成立的索引。

    Select * from employee
    where
    first_name ='Beill' and last_name ='Cliton' 

    遇到上面这种状况又怎样处置惩罚呢?假定一个变量(name)中存放着Bill Cliton这个员工的姓名,对付这种状况我们又怎样住手全程遍历,运用索引呢?可以运用一个函数,将变量name中的姓和名分隔隔离分手就可以了,可是有一点需求注重,这个函数是不能浸染在索引列上。上面是SQL查询剧本:

    select * from employee
    where
    first_name = SUBSTR('&&name',1,INSTR('&&name',' ')-1)
    and
    last_name = SUBSTR('&&name',INSTR('&&name’,' ') 1) 

    3. 带通配符(%)的like语句

    异样以上面的例子来看这种状况。今朝的需求是多么的,要求退职工表中查询名字中包罗cliton的人。可以给与如下的查询SQL语句:

    select * from employee where last_name like '%cliton%' 

    这里因为通配符(%)在搜索词首泛起,以是Oracle体系不运用last_name的索引。在许多状况下可以无法住手这种状况,可是一定要心中有底,通配符如此运用会降低查询速度。可是当通配符出今朝字符串其他位置时,优化器就能操纵索引。在上面的查询中索引获得了运用:

    select * from employee where last_name like 'c%' 

    4. Order by语句

    ORDER BY语句决定了Oracle怎样将前往的查询成果排序。Order by语句对要排序的列没有什么分外的限制,也可以将函数加出列中(象联接年夜要附加等)。任安在Order by语句的非索引项年夜要有比赛争论表达式都将降低查询速度。

    细心反省order by语句以找出非索引项年夜要表达式,它们会降低功用。处置惩罚这个问题的举措便是重写order by语句以运用索引,也可觉得所运用的列成立别的一个索引,同时应绝对住手在order by子句中运用表达式。

    5. NOT

    我们在查询时经常在where子句运用一些逻辑表达式,如年夜于、小于、等于以及不等于等等,也可以运用and(与)、or(或)以及not(非)。NOT可用来对任何逻辑运算标记取反。上面是一个NOT子句的例子:

    ... where not (status ='VALID') 

    假定要运用NOT,则应在取反的短语前面加上括号,并在短语前面加上NOT运算符。NOT运算符包罗在别的一个逻辑运算符中,这便是不等于(<>)运算符。换句话说,即便不在查询where子句中显式地参预NOT词,NOT仍在运算符中,见下例:

    ... where status <>'INVALID' 

    再看上面这个例子:

    select * from employee where salary<>3000; 

    对这个查询,可以改写为不运用NOT:

    select * from employee where salary<3000 or salary>3000; 

    固然这两种查询的成果一样,可是第二种查询方案会比第一种查询方案更快些。第二种查询答应Oracle对salary列运用索引,而第一种查询则不能运用索引。

    6. IN和EXISTS

    有工夫会将一列和一系列值比拟较。最庞年夜的举措便是在where子句中运用子查询。在where子句中可以运用两种把戏的子查询。

    第一种把戏是运用IN操作符:

    ... where column in(select * from ... where ...); 

    第二种把戏是运用EXIST操作符:

    ... where exists (select 'X' from ...where ...); 

    我信任绝年夜年夜都人会运用第一种把戏,因为它对照等闲编写,而现实上第二种把戏要远比第一种把戏的遵命高。在Oracle中可以简直将一切的IN操作符子查询改写为运用EXISTS的子查询。

    第二种把戏中,子查询以‘select 'X'初阶。运用EXISTS子句非论子查询从表中抽取什么数据它只反省where子句。多么优化器就不用遍历整个表而仅依照索引就可完成任务(这里假定在where语句中运用的列存在索引)。相对付IN子句来说,EXISTS运用相连子查询,结构起来要比IN子查询艰巨一些。

    经由运用EXIST,Oracle体系会首先反省主查询,然后运转子查询直到它找到第一个婚配项,这就节流了工夫。Oracle体系在执行IN子查询时,首先执行子查询,并将获得的成果列表存放在在一个加了索引的一时表中。在执行子查询之前,体系先将主查询挂起,待子查询执行终了,存放在一时表中今后再执行主查询。这也便是运用EXISTS比运用IN伟年夜查询速度快的缘故起因。

    同时应尽可以运用NOT EXISTS来取代NOT IN,固然二者都运用了NOT(不能运用索引而降低速度),NOT EXISTS要比NOT IN查询遵命更高




    版权声明: 原创作品,答应转载,转载时请务必以超链接方法标明文章 原始来由 、作者信息和本声明。否则将穷究功令责任。

  • 相关阅读:
    JavaScript 时间帮助封装
    EntityFramework 基类重写
    sql server 大数据, 统计分组查询,数据量比较大计算每秒钟执行数据执行次数
    C# DataTable 转实体对象
    EF自动创建数据库步骤之四(启用数据库初始器)
    EF自动创建数据库步骤之三(自定义数据库初始器)
    EF自动创建数据库步骤之二(继承DbContext类)
    EF自动创建数据库步骤之一(实体类写法)
    十大排序算法_java实现
    位运算
  • 原文地址:https://www.cnblogs.com/zgqjymx/p/1976716.html
Copyright © 2011-2022 走看看