欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

数据库之Oracle-第3篇-查询

程序员文章站 2022-06-01 19:46:51
...

a.查询关键字

SELECT
	DISTINCT
	AS
	聚合函数(COUNT() MAX() MIN() SUM() AVG())
FROM 
	WHERE
	GROUP BY 
		规则:除聚合函数外 显示列必须是分组列
		意义:目的为了聚合统计
	HAVING
		对聚合后的数据进一步筛选
	ORDER BY

b.模糊查询

LIKE
通配符 % _

c.多表查询

"外键" 关系明确
分清主次 首选外联接

d.子查询

理论依据->前一次查询结果可以作为下次查询条件(等量代换)
伪列:
分页:
	RowNum
		特点:当数据查询产生后进行动态编号 从1开始
	排序顺序
		先查询完 [RowNum产生] 在排序
	/*
  scott 用例
  dept 部门表
       deptno 部门编号  
       dname  部门名称
       loc    部门所在地
  emp 员工表
       empno  员工工号
       ename  姓名
       job    职位
       mgr    直接上司工号
       hiredate 入职时间
       sal      底薪
       comm     奖金
       deptno   所在部门编号(外键)
*/
--基础sql准备
--常规用户登录
--请输入用户名:
username/password
system/admin
--SQL>
conn username/password
conn system/admin
--查看当前用户
show user;
--创建表空间
create tablespace tablespace_name  datafile 'path' size [32k~128G] autoextend on/off;
create tablespace test datafile 'c:/test.dbf' size 1m autoextend on;
--创建用户
create user username identified by password default tablespace tablespace_name ;
create user lichee identified by admin default tablespace test;
--授登录和资源权限
grant connect,resource to username;
grant connect,resource to lichee;
--断开连接
disconnect
disconn
--常规用户登录
--请输入用户名:
username/password
lichee/admin
--SQL>
conn username/password
conn lichee/admin
--查看当前用户
show user;
--删除约束
--删除外键约束
alter table emp drop constraint fk_emp;
--删除主键约束
alter table emp drop constraint pk_emp;
alter table dept drop constraint pk_dept;

--删除表
drop table bonus;
drop table salgrade;
drop table dept;
drop table emp;

--创建bonus表
create table bonus (
	ename varchar2(10 byte) null ,
	job varchar2(9 byte) null ,
	sal number null ,
	comm number null 
);

--创建dept表
create table dept (
	deptno number(2) not null ,
	dname varchar2(14 byte) null ,
	loc varchar2(13 byte) null 
);

--创建emp表
create table emp (
	empno number(4) not null ,
	ename varchar2(10 byte) null ,
	job varchar2(9 byte) null ,
	mgr number(4) null ,
	hiredate date null ,
	sal number(7,2) null ,
	comm number(7,2) null ,
	deptno number(2) null 
);

--创建salgrade表
create table salgrade (
	grade number null ,
	losal number null ,
	hisal number null 
);


--插入数据dept表
insert into dept values ('10', 'accounting', 'new york');
insert into dept values ('20', 'research', 'dallas');
insert into dept values ('30', 'sales', 'chicago');
insert into dept values ('40', 'operations', 'boston');

--插入数据emp表
insert into emp values ('7369', 'smith', 'clerk', '7902', to_date('1980-12-17 00:00:00', 'yyyy-mm-dd hh24:mi:ss'), '800', null, '20');
insert into emp values ('7499', 'allen', 'salesman', '7698', to_date('1981-02-20 00:00:00', 'yyyy-mm-dd hh24:mi:ss'), '1600', '300', '30');
insert into emp values ('7521', 'ward', 'salesman', '7698', to_date('1981-02-22 00:00:00', 'yyyy-mm-dd hh24:mi:ss'), '1250', '500', '30');
insert into emp values ('7566', 'jones', 'manager', '7839', to_date('1981-04-02 00:00:00', 'yyyy-mm-dd hh24:mi:ss'), '2975', null, '20');
insert into emp values ('7654', 'martin', 'salesman', '7698', to_date('1981-09-28 00:00:00', 'yyyy-mm-dd hh24:mi:ss'), '1250', '1400', '30');
insert into emp values ('7698', 'blake', 'manager', '7839', to_date('1981-05-01 00:00:00', 'yyyy-mm-dd hh24:mi:ss'), '2850', null, '30');
insert into emp values ('7782', 'clark', 'manager', '7839', to_date('1981-06-09 00:00:00', 'yyyy-mm-dd hh24:mi:ss'), '2450', null, '10');
insert into emp values ('7788', 'scott', 'analyst', '7566', to_date('1987-04-19 00:00:00', 'yyyy-mm-dd hh24:mi:ss'), '3000', null, '20');
insert into emp values ('7839', 'king', 'president', null, to_date('1981-11-17 00:00:00', 'yyyy-mm-dd hh24:mi:ss'), '5000', null, '10');
insert into emp values ('7844', 'turner', 'salesman', '7698', to_date('1981-09-08 00:00:00', 'yyyy-mm-dd hh24:mi:ss'), '1500', '0', '30');
insert into emp values ('7876', 'adams', 'clerk', '7788', to_date('1987-05-23 00:00:00', 'yyyy-mm-dd hh24:mi:ss'), '1100', null, '20');
insert into emp values ('7900', 'james', 'clerk', '7698', to_date('1981-12-03 00:00:00', 'yyyy-mm-dd hh24:mi:ss'), '950', null, '30');
insert into emp values ('7902', 'ford', 'analyst', '7566', to_date('1981-12-03 00:00:00', 'yyyy-mm-dd hh24:mi:ss'), '3000', null, '20');
insert into emp values ('7934', 'miller', 'clerk', '7782', to_date('1982-01-23 00:00:00', 'yyyy-mm-dd hh24:mi:ss'), '1300', null, '10');

--插入数据salgrade表
insert into salgrade values ('1', '700', '1200');
insert into salgrade values ('2', '1201', '1400');
insert into salgrade values ('3', '1401', '2000');
insert into salgrade values ('4', '2001', '3000');
insert into salgrade values ('5', '3001', '9999');

--添加emp主键empno
alter table emp add constraint pk_emp primary key (empno);
--添加dept主键deptno
alter table dept add constraint pk_dept primary key (deptno);
--添加emp.deptno外键dept.deptno
alter table emp add constraint fk_emp foreign key (deptno) references dept (deptno);


---------------------------------------------------------

--设置显示长度
set linesize 200;
--设置显示行数
set pagesize 100;
--查询关键字
--请列举所有职位
select distinct job as 职位 from emp;

--请列举底薪在1000~2000之间的员工信息
select * from emp where sal between 1000 and 2000;
select * from emp where sal >= 1000 and sal <= 2000;

--请列举每个员工的薪水
--注意:任何数据与null运算结果为null
select 1+null from dual;
--函数 nvl(exp,value)
--如果exp为null 返回value 否则返回exp
select ename,sal+nvl(comm,0) as salary from emp;

--请列举没有奖金的员工信息
select * from emp where comm is null;
select * from emp where comm is not null;

--注意:误区"分组"
select * from emp order by job;

--数据库分组的规则
--除聚合函数外,显示列必须是分组列
--数据库分组的意义
--为了统计聚合
--请统计每个职位有多少人
select job,count(empno) from emp group by job;

--以下两种结果是不一样的
select job,deptno,count(empno) from emp group by job,deptno;
select deptno,job,count(empno) from emp group by deptno,job;

--请列举超过两人以上的职位
--where 对原始数据进行条件筛选
--having 对聚合后的数据进一步筛选
select job,count(empno) from emp group by job having count(empno)>2;

----------------------------------------------------------------
--模糊查询
--请列举工号第二位是3的所有员工
-- % 匹配任意长度字符
-- _ 匹配任意单个字符
select * from emp where empno like '_3%';
--请列举名字第二位是“l”或者“o”的所有员工
select * from emp where ename like '_l%' or ename like '_o%';
--请列举名字第二位不是“l”的所有员工
select * from emp where ename not like  '_l%'

----------------------------------------------------------------
--多表查询 原则:首选外联接

--请列举所有员工姓名及其所属的部门名称
select ename,dname from emp,dept where emp.deptno = dept.deptno;
--员工必定所属部门 
select ename,dname from emp left join dept on emp.deptno = dept.deptno;

--请列举所有部门名称及其对应的员工姓名
select dname,ename from emp,dept where emp.deptno = dept.deptno;
--部门未必有员工 
--外联接特点:主表数据必须显示,如果没有字表数据,使用null值填充
select dname,ename from emp right join dept on emp.deptno = dept.deptno;

--请列举员工和其直属上司的名字
select e1.ename,e2.ename from emp e1 left join emp e2 on e1.mgr=e2.empno;

--请列举没有员工的部门
select dname,ename from emp right join dept on emp.deptno = dept.deptno where ename is null;
--分析员工表 deptno
--在员工表出现过的部门编号
select distinct deptno from emp;
--分析部门表 
select * from dept where deptno not in (select distinct deptno from emp);

--关于分页
--每页5条记录 显示第二页

--知识点:伪列
--rowid 记录添加到表空间 系统唯一物理地址编码 不会因为数据变化而修改 通过该信息查找效率最快 
--rownum 序号 根据查询结果而依次进行的编号 该编号与查询出现的记录顺序相关 
select rowid,rownum,emp.* from emp; 
select rowid,rownum,emp.* from emp where sal >1500; 

--通过子查询固定rownum
select * from 
(select rownum rn,emp.* from emp) where rn between 6 and 10;

--推荐 (自然排名分页)
select * from 
(select rownum rn,emp.* from emp where rownum<=10) where rn >5;

--按sal降序排列 获取第二页
--排序规则 先按自然排名查询后在进行规则排序
select rownum,emp.* from emp order by sal desc;

select * from 
(select rownum as rn,t.* from (select * from emp order by sal desc) t where rownum<=10)
where rn >5;

select * from 
(select rownum as rn,t.* from (select * from emp order by sal desc) t)
where rn >5 and rn<=10;

select * from dept;
select * from emp;
--1) 查询一共有多少员工
select count(empno) from emp;
--2) 查询每个员工的工龄 
select empno,ename,hiredate,floor(months_between(sysdate,hiredate)/12) from emp;
--3) 查询每个部门有多少人
select dept.deptno,dname,nvl(ct,0) from dept left join
(select deptno,count(empno) ct from emp group by deptno) e 
on dept.deptno=e.deptno;
--4) 查询工号第三位为8的所有员工
select * from emp where empno like '__8%';
--5) 查询每个员工和直接上司
select e1.ename,e2.ename from emp e1 left join emp e2
on e1.mgr = e2.empno;
--6) 查询员工所对应的部门
select ename,dname from emp left join dept on emp.deptno = dept.deptno;
--7) 查询部门所对应的员工 
select dname,ename from emp right join dept on emp.deptno = dept.deptno;
--8) 查询哪个部门没有员工
select * from dept where deptno not in
(select distinct deptno from emp);
--9) 统计哪个部门的平均工资超过2200
select * from dept where deptno in
(select deptno from emp group by deptno having avg(sal+nvl(comm,0))>=2200);
--10)统计每个职位有多少人并降序排列
select job,count(empno) ct from emp group by job order by ct desc;

------------------
--分页
--RowNum

--自然排序
select * from 
(select rownum rn,emp.* from emp where rownum<=10)
where rn>5;

--自定义排序(通用)
--排序顺序
select * from 
(select rownum rn,e.* from 
(select emp.* from emp order by sal desc) e where rownum<=10)
where rn>5; 

-------------------
--排序函数
select empno,ename,sal,
row_number() over(order by sal desc) rn1,
rank() over(order by sal desc) rn2,
dense_rank() over(order by sal desc) rn3
from emp;

--分组排序函数
select empno,ename,deptno,sal,
rank() over(partition by deptno order by sal desc) rn2
from emp;

--------------------
--笔试1
--学生考试成绩表  获取成绩排名第三的学生信息
--类似 底薪排名第三的员工信息
select * from 
(select empno,ename,sal,
rank() over(order by sal desc) rn2
from emp) where rn2=3;

--笔试2
--现存一张表 (没有主键 有很多重复数据) 要求删除重复数据
/*
     名称                        名称
     张三                        张三
     李四                ->      李四
     王五                        王五
     张三
     李四
     张三          
*/
create table tb_student
(
       sname VARCHAR2(50)
);

INSERT INTO tb_student VALUES('张三');
INSERT INTO tb_student VALUES('李四');
INSERT INTO tb_student VALUES('王五');
INSERT INTO tb_student VALUES('张三');
INSERT INTO tb_student VALUES('李四');
INSERT INTO tb_student VALUES('张三');
commit;

delete from tb_student where rowid in
(select rowid from 
(select sname,row_number() over(partition by sname order by sname) rn from tb_student)
where rn>1);

select * from tb_student;

相关标签: 查询