day45 数据库总结

一、加密算法

  1. md5(str) 最经典,做常用的加密方式

    1. 创建数据表user
            create table user(
                id int primary key auto_increment,
                name varchar(30),
                password varchar(50)
            );
    2. 在user中插入数据
        insert into user values(null,'兰博文','358972');
        
        insert into user values(null,'李龙龙',md5('123456'));
  2. sha(str) 返回40位十六进制的字符串密码

    insert into user values(null,'李俊坤',sha('123456'));  
  3. sha256(str,hash_length)

    insert into user values(null,'鲍煜',sha2('123456',0));

二、系统函数信息

  1. database() 返回当前数据库名

    select database(); 
  2. version() 返回当前数据库版本

    select version();
  3. user() 返回当前登录用户名

    select user();

三、数学相关函数

  • 向下取整 floor(num)

    select floor(3.84);  3
  • 四舍五入 round(num)

    select round(23.8);  24
  • round(num,m)

    select round(23.879,2); 23.88
  • 非四舍五入

    select truncate(23.879,2); 23.87
  • 随机数 rand() 0-1

    获取3、4、5 随机数

    select floor(rand()*3)+3;

四、分组查询

  • group by 字段;

  • 将某个字段的相同值分为一组,对其它字段的数据进行聚合函数的统计,称为分组查询

    1. 查询每个部门的平均工资

      select deptno,avg(sal) from emp group by deptno;
    2. 查询每个职位的最高工资

      sel ect job,max(sal) from emp group by job;
    3. 查询每个部门的人数

      sel ect deptno,count(*) from emp group by deptno;
    4. 查询每个职位中工资大于1000的人数

      sel ect job,count(*) from emp where sal>1000 group by job;
    5. 查询每个领导的手下人数

      sel ect mgr,count(*) from emp where mgr is not null group by mgr;
  • 多字段分组查询

    select deptno,gender,max(age) from emp group by deptno,gender;
    1. 查询每个部门每个主管的手下人数

      sel ect deptno,mgr,count(*) from emp where mgr is not null group by deptno,mgr;

五、having

  • having后面可以写普通字段的条件也可以写聚合函数的条件,但是不推荐在having后面写普通字段的条件

  • where后面不能写聚合函数的条件

  • having要结合分组查询使用

    1. 查询每个部门的平均工资,要求平均工资大于2000.

      • 错误写法(where后面不能写聚合函数)

        select deptno,avg(sal) from emp where avg(sal)>2000 group by deptno;
      • 正确写法:

        select deptno,avg(sal) a from emp group by deptno having a>2000;
    2. 查询t_item表中每个分类category_id的平均单价要求平均单价低于100

      select category_id,avg(price) a 
      from t_item 
      group by category_id 
      having a<100;
    3. 查询emp表中工资在1000-3000之间的员工,每个部门的编号,工资总和,平均工资,过滤掉平均工资低于2000的部门,按照平均工资进行降序排序

      select deptno,sum(sal),avg(sal) a 
      from emp 
      where sal between 1000 and 3000 
      group by deptno 
      having a>=2000 
      order by a desc;
    4. 查询emp表中每个部门的平均工资高于2000的部门编号,部门人数,平均工资,最后根据平均工资降序排序

      select deptno,count(*),avg(sal) a 
      from emp 
      group by deptno 
      having a>2000 
      order by a desc;
    5. 查询emp表中不是以s开头,每个职位的名字,人数,工资总和,最高工资,高滤掉平均工资是3000的职位,根据人数升序排序 如果人数一致则根据工资总和降序排序

      select job,count(*) c,sum(sal) s,max(sal) 
      from emp 
      where job not like 's%' 
      group by job 
      having avg(sal)!=3000 
      order by c,s desc;
    6. 查询emp表中每年入职的人数。

      select extract(year from hiredate) year,count(*) 
      from emp group by year;
    7. 查询每个部门的最高平均工资(提高题)

      select avg(sal) a 
      from emp 
      group by deptno 
      order by a 
      desc limit 0,1;
    8. 拿最高平均工资的部门编号 (并列第一的问题无法解决)

      select deptno 
      from emp 
      group by deptno 
      order by avg(sal)
      desc limit 0,1;

六、子查询(嵌套查询)

  1. 查询emp表中工资最高的员工信息

    select max(sal) from emp;
     select * from emp where sal=5000;
    • 通过子查询把上面两条合并成一条

      select * from emp where sal=(select max(sal) from emp);
  2. 查询emp表中工资大于平均工资的所有员工的信息

    select avg(sal) from emp; 
    select * from emp where sal>
    (select avg(sal) from emp);
  3. 查询工资高于20号部门最高工资的所有员工信息

    select max(sal) from emp where deptno=20;
     select * from emp where sal>
     (select max(sal) from emp where deptno=20);
  4. 查询和jones相同工作的其他员工信息

    select job from emp where ename='jones';
    select * from emp where job=
    (select job from emp where ename='jones') 
    and ename!='jones';
  5. 查询工资最低的员工的同事们的信息(同事=相同job)

    • 得到最低工资

      select min(sal) from emp;
    • 得到最低工资哥们的工作

      select job from emp where sal=
      (select min(sal) from emp);
    • 通过工作找到同事们 还要排除最低工资那哥们儿

      select * from emp where job=
      (select job from emp where sal=
      (select min(sal) from emp)) and sal!=
      (select min(sal) from emp);
  6. 查询最后入职的员工信息

    select max(hiredate) from emp;
    select * from emp where hiredate=
    (select max(hiredate) from emp);
  7. 查询员工king的部门编号和部门名称(需要用到dept表)

    select deptno from emp where ename='king';
    ​
    select deptno,dname from dept where deptno=
    (select deptno from emp where ename='king');
  8. 查询有员工的部门信息

    • 查询员工表中出现的部门编号

      select distinct deptno from emp;  
      ​
      select * from dept where deptno in 
      (select distinct deptno from emp);
  9. 查找平均工资最高的部门信息 (最大难度,需要考虑并列第一问题)

    • 得到最高平均工资

      select avg(sal) from emp 
      group by deptno order by avg(sal) 
      desc limit 0,1;
    • 通过平均工资找到部门编号

      select deptno from emp 
      group by deptno having avg(sal)=
      (select avg(sal) from emp 
      group by deptno order by avg(sal) 
      desc limit 0,1); 
    • 通过部门编号查询部门信息

      select * from dept where deptno in(上面一坨);  
      ​
      select * from dept where deptno in
      (select deptno from emp group by 
      deptno having avg(sal)=
      (select avg(sal) from emp 
      group by deptno order by avg(sal) desc 
      limit 0,1));
  • 子查询总结:

    1. 嵌套在SQL语句中的查询语句称为子查询

    2. 子查询可以嵌套n层

    3. 子查询可以写在哪些位置?

      • 写在where或having后面作为查询条件的值

      • 写在from后面当成一张表使用 必须有别名

        select * from emp where deptno=20;  
        ​
        select ename from 
        (select * from emp where deptno=20) t1;
      • 写在创建表的时候

        create table newemp as 
        (select ename,sal,deptno 
        from emp where deptno=20);

七、关联查询

  • 同时查询多张表的查询方式称为关联查询

    1. 查询每一个员工姓名和其对应的部门名称

      select e.ename,d.dname 
      from emp e,dept d where e.deptno=d.deptno;
    2. 查询在new york工作的所有员工的信息

      select e.* from emp e,dept d 
      where e.deptno=d.deptno and d.loc='new york';
    3. 查询价格在50以内的商品标题和商品分类名称

      select i.title, c.name  
      from t_item i ,t_item_category c 
      where i.category_id= c.id  and i.price<50;
笛卡尔积
  • 如果关联查询不写关联关系,则得到两张表结果的乘积,这个乘积称为笛卡尔积

  • 笛卡尔积是错误的查询方式导致的结果,工作中切记不要出现

八、等值连接和内连接

  • 这两种查询方式得到的结果是一样的

    1. 等值连接:

      select * from A,B where A.x=B.x and A.age=18;
    2. 内连接:

      select * from A join B on A.x=B.x where A.age=18;
      • 查询每一个员工姓名和其对应的部门名称

        select e.ename,d.dname 
        from emp e 
        join dept d 
        on e.deptno=d.deptno;

九、外链接

查询A,B两张表的数据,如果查询两张表的交集数据使用内连接或等值连接,如果查询某一张表的全部数据另外一张表的交集数据则用外链接

  • 左外链接:

    select * from A left join B on A.x=B.x where A.age=18;
  • 右外链接:

    select * from A right join B on A.x=B.x where A.age=18;
    1. 查询所有员工和对应的部门名称

      • 插入新数据

        insert into emp (empno,ename,sal) values(10010,'Tom',500);  
        ​
        select e.ename,d.dname from emp e left join dept d on e.deptno=d.deptno;
    2. 查询所有部门名称和对应的员工姓名

      select e.ename,d.dname from emp e right join dept d on e.deptno=d.deptno;

十、关联查询总结:

  • 关联查询的查询方式:1. 等值连接 2.内连接 3.外链接(左外和右外)

  • 查询两张表的交集用等值或内连接,推荐使用内连接

  • 查询一张表的全部数据和另外一张表的交集数据使用外链接

你可能感兴趣的:(数据库,sql,oracle)