Mysql 初级需要注意的点
sql的分类
- DQL(Data Query Language)数据查询语言,对数据只查询,不修改,保留字有select、from、where、group by、having、order by
- DDL(Data Definition Language)数据定义语言,负责数据结构定义与数据库对象定义的语言。由create、alter、drop三个语法组成
- DML(Data Manipilation Language)数据操纵语言,以insert、update、delete三种指令为核心。
- DCL(Data Control Language)数据控制语言,是对数据访问权进行控制的指令,由grant(授权)和revoke(撤销授权)指令组成
- TPL(Transaction Processing Language)数据事务管理语言,它能确保被DML语句影响的表的所有行及时得以更新,TPL语句包括begin、transaction、commit、rollback
- CCL(Cursor Control Language)指针控制语言,语句包括declare cursor、fetch into 和update current 用于对一个或多个表单独行的操作。
查询条件and 和or的优先级问题
and和or同时出现,and的优先级较高,会先执行,如果希望or先执行,这时给or条件加小括号就行。
select
ename,sal,deptno
from
emp
where
sal < 1500 and (deptno = 20 or deptno = 30);
查询条件in 、not in 与null
select * from emp where comm in (NULL, 300); -- 语句的执行原理实际上是执行
select * from emp where comm = NULL or comm = 300;
其中null不能用等号直接判断,需要使用is null,所以comm = NULL 结果是false,所以被忽略
所以 in 是自动忽略null的
select * from emp where comm not in(NULL, 300);
-- not in的执行原理实际上是采用<>和and的方式,也就是说,以上SQL语句实际上是:
select * from emp where comm <> NULL and comm <> 300;
NULL的判断不能使用<>,所以comm <> NULL结果是false,由于后面是and,and表示并且,comm <> NULL已经是false了,所以and右边的就没必要运算了,comm <> NULL and comm <> 300的整体运算结果就是false。所以查询不到任何数据。
所以not in是不会自动忽略NULL的
in和or的效率比拼
在MySQL当中,如何统计一个SQL语句的执行时长?
可以使用这个命令:show profiles; 这个命令可以查看在mysql中执行的所有SQL以及命令的耗费时长。
or的效率为O(n),而in的效率为O(log n), 当n越大的时候效率相差越明显(也就是说数据量越大的时候,in的效率越高)
查询员工名字中第二个字母是'A'的员工姓名
select ename from emp where ename like '_A%';
where和order by的位置
select ename,sal from emp where job = 'MANAGER' order by sal asc;
where先执行,order by语句是最后执行的。
distinct 去重
select distinct job from emp; -- 执行成功
select ename, distinct job from emp; -- 报错
-- distinct只能出现在所有字段的最前面。
-- 当distinct出现后,后面多个字段一定是联合去重的,比如:
select distinct depart,job from emp
空处理函数 ifnull
ifnull(x, y),空处理函数,当x为NULL时,将x当做y处理。
ifnull(comm, 0),表示如果员工的津贴是NULL时当做0处理。
select ename,(sal + ifnull(comm,0))*12 as yearsal from emp
now()和sysdate()的区别:
- now():获取的是执行select 语句的时刻
- sysdate():获取的是执行sysdate()函数的时刻
select current_date() -- 获取当前日期
select curtime() -- 获取当前时间
select datediff('1979-02-01 22:12:21','1983-01-01) -- 计算两个日期之间所差天数,不算时分秒
SELECT IF(500<1000, "YES", "NO"); -- 如果条件为TRUE则返回“YES”,如果条件为FALSE则返回“NO”:
分组函数
分组函数组合使用
select count(*),max(sal),min(sal),avg(sal),sum(sal) from emp;
分组函数注意事项
分组函数不能直接使用在where子句当中
分组查询
group by
group by的执行是在where之后执行。
找出每个部门不同岗位的平均薪资
select deptno,job,avg(sal) from emp group by deptno,job;
当select语句中有group by的话,select后面只能跟分组函数或参加分组的字段
select ename,deptno,avg(sal) from emp group by deptno; -- 这个SQL执行后会报错。
having
having写在group by的后面,当你对分组之后的数据不满意,可以继续通过having对分组之后的数据进行过滤。
where的过滤是在分组前进行过滤。
使用原则:尽量在where中过滤,实在不行,再使用having。越早过滤效率越高。
找出除20部门之外,其它部门的平均薪资。
select deptno,avg(sal) from emp where deptno<>20 group by deptno; // 建议
select deptno,avg(sal) from emp group by deptno having deptno <> 20; // 不建议
查询每个部门平均薪资,找出平均薪资高于2000的。
select deptno,avg(sal) from emp group by deptno having avg(sal) > 2000;
组内排序
案例:找出每个工作岗位的工资排名在前两名的。
group_concat 分组拼接员工编号,员工按工资倒叙。SUBSTRING_INDEX 截取前两名员工。
select SUBSTRING_INDEX(group_concat(empno ORDER BY sal desc),',',2) from emp GROUP BY job
in和exists区别
IN 和 EXISTS 都是用于关系型数据库查询的操作符。不同之处在于:
- IN 操作符是根据指定列表中的值来判断是否满足条件,而 EXISTS 操作符则是根据子查询的结果是否有返回记录集来判断。
- EXISTS 操作符通常比 IN 操作符更快,尤其是在子查询返回记录数很大的情况下。因为 EXISTS 只需要判断是否存在符合条件的记录,而 IN 操作符需要比对整个列表,因此执行效率相对较低。
- IN 操作符可同时匹配多个值,而 EXISTS 只能匹配一组条件。
union&union all
不管是union还是union all都可以将两个查询结果集进行合并。
union会对合并之后的查询结果集进行去重操作。
union all是直接将查询结果集合并,不进行去重操作。(union all和union都可以完成的话,优先选择union all,union all因为不需要去重,所以效率高一些。)
案例:查询工作岗位是MANAGER和SALESMAN的员工。
select ename,sal from emp where job='MANAGER'
union all
select ename,sal from emp where job='SALESMAN';
以上案例采用or也可以完成,那or和union all有什么区别?考虑走索引优化之类的选择union all,其它选择or。
本文来自博客园,作者:NE_STOP,转载请注明原文链接:https://www.cnblogs.com/alineverstop/p/21465464
浙公网安备 33010602011771号