05.高级查询

01使用GROUP BY子句实现分组

SELECT MAX(AGE) AS 最大年龄, DEPT AS 所在班级
FROM STU
GROUP BY DEPT;

02按条件查询并分组

SELECT MAX(AGE) AS 最大年龄, DEPT AS 所在班级
FROM STU
WHERE GENTLE = '男'
GROUP BY DEPT;

03使用CUBE汇总数据

SELECT NO AS 学号, DEPT AS 所在班级, AVG(AGE) AS 平均年龄, GROUPING(NO), GROUPING(DEPT)
FROM STU 
GROUP BY CUBE(DEPT, NO);
--CUBE参数的作用除了返回GROUP BY子句指定列外,还返回按组统计的行,
--返回结果先按分组的第一个条件NO列排序显示,再按第二个条件DEPT列排序显示以此类推
--GROUPING用来判断某行数据是不是按照ROLLUP或CUBE进行汇总,返回0或1,
--1表示指定列由于汇总符产生NULL值,也表示汇总时忽略该列。

04使用ROLLUP汇总数据

SELECT NO AS 学号, DEPT AS 所在班级, AVG(AGE) AS 平均年龄, GROUPING(NO), GROUPING(DEPT)
FROM STU 
GROUP BY ROLLUP(DEPT, NO)
ORDER BY NO, DEPT;

05使用HAVING子句过滤分组数据

SELECT MAX(AGE) AS 最大年龄,
DEPT AS 所在班级
FROM STU 
GROUP BY DEPT HAVING MAX(AGE) >=25;

06区别HAVING与WHERE子句

 

 

07使用ORDER BY子句排序

SELECT * FROM STU 
ORDER BY GENTLE ASC, AGE DESC;--ASC升序,默认可省略;DESC降序

08MINUS(补集)

返回第一个查询结果的记录减去第二个查询结果的记录;查询列要一致

 

 

09INTERSECT(交集)

10UNION ALL / UNION(并集)

 

11无条件多表查询

SELECT S.NO AS 学号, S.NAME AS 姓名, G.NAME AS 学科, G.SCORE AS 成绩
FROM STU S, GRADE G;

 查笛卡尔积 表行数相乘

12有共有字段的表等值查询

SELECT STU.*, GRADE.*
FROM STU, GRADE
WHERE STU.NO =GRADE.NO;
--先取STU表中的第一个NO记录值与GRADE表中的所有的NO值一一比较,将相等的选出,
--再取STUdents第一个NO记录值与GRADE表中的所有的NO值一一比较,将相等的选出,以此类推,
--运算符两边至少要有一个相等的记录,否则查询记录为空。

13含条件的等值查询

SELECT STU.*, GRADE.*
FROM STU, GRADE
WHERE STU.NO =GRADE.NO
AND STU.NAME = '张清';

14有共有字段的表非等值连接

SELECT STU.*, GRADE.*
FROM STU, GRADE
WHERE STU.NO <> GRADE.NO;
--相当与无条件连接的查询结果集减去等值查询结果集

15两个表内连接

SELECT STU.*, GRADE.*
FROM STU INNER JOIN GRADE ON 
STU.NO = GRADE.NO;
--INNER JOIN关键字是SQL标准写法,INNER可省略
--等值连接与非等值连接都属于内连接。指多个表的相关字段满足连接条件时,
--则从这两个表中提取数据并组合成新的记录。

16表自连接

SELECT S1.NO AS 学号, S1.NAME AS 姓名, S1.AGE AS 年龄
FROM STU S1 INNER JOIN STU S2
ON S1.AGE = S2.AGE
WHERE S1.NO <> S2.NO
ORDER BY S1.AGE DESC;
--查询STU表中年龄相同的结果集

17表左外连接

SELECT STU.*, GRADE.*
FROM STU LEFT OUTER JOIN GRADE
ON STU.NO = GRADE.NO;
--OUTER可省略
--OR
SELECT STU.*, GRADE.*
FROM STU, GRADE
WHERE STU.NO = GRADE.NO(+);
--左外连接结果集包括LEFT JOIN子句中指定的左表(主表)的所有行,
--如果左表的某行在右表中没有匹配行,则在相关联的结果集中右表所有选择列均为空值

18表右外连接

SELECT STU.*, GRADE.*
FROM STU RIGHT OUTER JOIN GRADE
ON STU.NO = GRADE.NO;
--OUTER可省略
--OR
SELECT STU.*, GRADE.*
FROM STU, GRADE
WHERE STU.NO(+) = GRADE.NO;
--右表(GRADE)为主表

19表全外连接

SELECT STU.*, GRADE.*
FROM STU FULL OUTER JOIN GRADE
ON STU.NO = GRADE.NO;
--全外连接操作产生的结果集不仅包括符合连接条件的匹配行,
--而且包括两个连表中的所有记录,与左外连接和右外连接不同的是全外连接还返回左右表中不符合查询条件的数据行,以空值补全对应行的列值

20多表连接

SELECT STU.*, GRADE.*, COURSE.*
FROM STU INNER JOIN GRADE
ON STU.NO = GRADE.NO
INNER JOIN COURSE
ON GRADE.NAME = COURSE.NAME
WHERE STU.NAME = '张清';
--OR
SELECT STU.*, GRADE.*, COURSE.*
FROM STU, GRADE, COURSE
WHERE STU.NO = GRADE.NO
AND GRADE.NAME = COURSE.NAME
AND STU.NAME = '张清';
--太多表进行连接将极大降低性能,一般select语句连接的表最多为8~10个,否则就要考虑数据库设计可能不是最优

DROP TABLE EMP CASCADE CONSTRAINTS;
CREATE TABLE EMP
(
  EMPNO     NUMBER(4),
  ENAME     VARCHAR2(10 BYTE),
  JOB       VARCHAR2(9 BYTE),
  MGR       NUMBER(4),
  HIREDATE  DATE,
  SAL       NUMBER(7,2),
  COMM      NUMBER(7,2),
  DEPTNO    NUMBER(2)
);
Insert into EMP
   (EMPNO, ENAME, JOB, MGR, HIREDATE, 
    SAL, DEPTNO)
 Values
   (7369, 'SMITH', 'CLERK', 7902, TO_DATE('1980/12/17', 'YYYY/MM/DD'), 
    800, 20);
Insert into EMP
   (EMPNO, ENAME, JOB, MGR, HIREDATE, 
    SAL, COMM, DEPTNO)
 Values
   (7499, 'ALLEN', 'SALESMAN', 7698, TO_DATE('1981/2/20', 'YYYY/MM/DD'), 
    1600, 300, 30);
Insert into EMP
   (EMPNO, ENAME, JOB, MGR, HIREDATE, 
    SAL, COMM, DEPTNO)
 Values
   (7521, 'WARD', 'SALESMAN', 7698, TO_DATE('1981/2/22', 'YYYY/MM/DD'), 
    1250, 500, 30);
Insert into EMP
   (EMPNO, ENAME, JOB, MGR, HIREDATE, 
    SAL, DEPTNO)
 Values
   (7566, 'JONES', 'MANAGER', 7839, TO_DATE('1981/4/2', 'YYYY/MM/DD'), 
    2975, 20);
Insert into EMP
   (EMPNO, ENAME, JOB, MGR, HIREDATE, 
    SAL, COMM, DEPTNO)
 Values
   (7654, 'MARTIN', 'SALESMAN', 7698, TO_DATE('1981/9/28', 'YYYY/MM/DD'), 
    1250, 1400, 30);
Insert into EMP
   (EMPNO, ENAME, JOB, MGR, HIREDATE, 
    SAL, DEPTNO)
 Values
   (7698, 'BLAKE', 'MANAGER', 7839, TO_DATE('1981/5/1', 'YYYY/MM/DD'), 
    2850, 30);
Insert into EMP
   (EMPNO, ENAME, JOB, MGR, HIREDATE, 
    SAL, DEPTNO)
 Values
   (7782, 'CLARK', 'MANAGER', 7839, TO_DATE('1981/6/9', 'YYYY/MM/DD'), 
    2450, 10);
Insert into EMP
   (EMPNO, ENAME, JOB, MGR, HIREDATE, 
    SAL, DEPTNO)
 Values
   (7788, 'SCOTT', 'ANALYST', 7566, TO_DATE('1982/12/9', 'YYYY/MM/DD'), 
    3000, 20);
Insert into EMP
   (EMPNO, ENAME, JOB, HIREDATE, SAL, 
    DEPTNO)
 Values
   (7839, 'KING', 'PRESIDENT', TO_DATE('1981/11/17', 'YYYY/MM/DD'), 5000, 
    10);
Insert into EMP
   (EMPNO, ENAME, JOB, MGR, HIREDATE, 
    SAL, COMM, DEPTNO)
 Values
   (7844, 'TURNER', 'SALESMAN', 7698, TO_DATE('1981/9/8', 'YYYY/MM/DD'), 
    1500, 0, 30);
Insert into EMP
   (EMPNO, ENAME, JOB, MGR, HIREDATE, 
    SAL, DEPTNO)
 Values
   (7876, 'ADAMS', 'CLERK', 7788, TO_DATE('1983/1/12', 'YYYY/MM/DD'), 
    1100, 20);
Insert into EMP
   (EMPNO, ENAME, JOB, MGR, HIREDATE, 
    SAL, DEPTNO)
 Values
   (7900, 'JAMES', 'CLERK', 7698, TO_DATE('1981/12/3', 'YYYY/MM/DD'), 
    950, 30);
Insert into EMP
   (EMPNO, ENAME, JOB, MGR, HIREDATE, 
    SAL, DEPTNO)
 Values
   (7902, 'FORO', 'ANALYST', 7566, TO_DATE('1981/12/3', 'YYYY/MM/DD'), 
    3000, 20);
Insert into EMP
   (EMPNO, ENAME, JOB, MGR, HIREDATE, 
    SAL, DEPTNO)
 Values
   (7934, 'MILLER', 'CLERK', 7782, TO_DATE('1982/1/23', 'YYYY/MM/DD'), 
    1300, 10);
COMMIT;

DROP TABLE GRADE CASCADE CONSTRAINTS;
CREATE TABLE GRADE
(
  NO     VARCHAR2(10 BYTE)                      NOT NULL,
  NAME   VARCHAR2(10 BYTE),
  SCORE  NUMBER
);
Insert into GRADE
   (NO, NAME, SCORE)
 Values
   ('120001', '计算机基础', 85);
Insert into GRADE
   (NO, NAME, SCORE)
 Values
   ('120003', '计算机基础', 96);
Insert into GRADE
   (NO, NAME, SCORE)
 Values
   ('120004', '计算机基础', 60);
COMMIT;

DROP TABLE COURSE CASCADE CONSTRAINTS;
CREATE TABLE COURSE(
NAME VARCHAR2(20),
SCORE NUMBER
);
INSERT INTO COURSE VALUES('计算机基础', 4);
INSERT INTO COURSE VALUES('数据结构', 4);
INSERT INTO COURSE VALUES('计算机英语', 2);
COMMIT;

DROP TABLE GROUP_BY_TEST CASCADE CONSTRAINTS;
CREATE TABLE GROUP_BY_TEST
(
  NAME    VARCHAR2(20 BYTE),
  CLASS   VARCHAR2(20 BYTE),
  ITEM    VARCHAR2(20 BYTE),
  OBJECT  VARCHAR2(20 BYTE),
  PRICE   NUMBER
);
Insert into GROUP_BY_TEST
   (NAME, CLASS, ITEM, OBJECT, PRICE)
 Values
   ('springy', '3C', 'phone', 'huawei', 4000);
Insert into GROUP_BY_TEST
   (NAME, CLASS, ITEM, OBJECT, PRICE)
 Values
   ('springy', '3C', 'phone', 'xiaomi', 3000);
Insert into GROUP_BY_TEST
   (NAME, CLASS, ITEM, OBJECT, PRICE)
 Values
   ('springy', '3C', 'computer', 'mac', 10000);
Insert into GROUP_BY_TEST
   (NAME, CLASS, ITEM, OBJECT, PRICE)
 Values
   ('springy', '3C', 'phone', 'thinkpad', 8000);
Insert into GROUP_BY_TEST
   (NAME, CLASS, ITEM, OBJECT, PRICE)
 Values
   ('springy', '3C', 'phone', 'huawei', 4000);
Insert into GROUP_BY_TEST
   (NAME, CLASS, ITEM, OBJECT, PRICE)
 Values
   ('springy', 'clothes', 'shoes', 'adidas', 300);
Insert into GROUP_BY_TEST
   (NAME, CLASS, ITEM, OBJECT, PRICE)
 Values
   ('springy', 'clothes', 'shoes', 'lining', 400);
Insert into GROUP_BY_TEST
   (NAME, CLASS, ITEM, OBJECT, PRICE)
 Values
   ('springy', 'clothes', 'pants', 'jackjones', 500);
Insert into GROUP_BY_TEST
   (NAME, CLASS, ITEM, OBJECT, PRICE)
 Values
   ('stephenson', 'clothes', 'shoes', 'adivon', 200);
Insert into GROUP_BY_TEST
   (NAME, CLASS, ITEM, OBJECT, PRICE)
 Values
   ('stephenson', 'clothes', 'shoes', 'nike', 300);
Insert into GROUP_BY_TEST
   (NAME, CLASS, ITEM, OBJECT, PRICE)
 Values
   ('stephenson', 'clothes', 'skirt', 'nike', 300);
Insert into GROUP_BY_TEST
   (NAME, CLASS, ITEM, OBJECT, PRICE)
 Values
   ('stephenson', 'clothes', 'skirt', 'adidas', 400);
COMMIT;

  

猜你喜欢

转载自www.cnblogs.com/weick/p/12778475.html