본문 바로가기
SQL/개념

03. 다중행 함수와 데이터 그룹화

by Merware 2023. 5. 3.

01. 하나의 열에 출력 결과를 담는 다중행 함수

1. 집계함수

SUM : 합계

COUNT : 데이터 개수

MAX : 최댓값

MIN : 최솟값

AVG : 평균값


1) SUM

SUM 함수를 사용하여 급여 합계 출력하기

-- 실습 7-1
SELECT SUM(SAL)
  FROM EMP;

SUM 함수를 사용하여 사원 이름과 급여 합계 출력하기

-- 실습 7-2
SELECT ENAME, SUM(SAL)
  FROM EMP;

추가 수당 합계 구하기

-- 실습 7-3
SELECT SUM(COMM)--NULL 존재(에러)
FROM EMP;

급여 합계 구하기(DISTINCT, ALL 사용)

-- 실습 7-4
SELECT SUM(DISTINCT SAL),
       SUM(ALL SAL),
       SUM(SAL)
  FROM EMP;

2) COUNT

EMP 테이블의 데이터 개수 출력하기

-- 실습 7-5
SELECT COUNT(*)
  FROM EMP;

부서 번호가 30번인 직원 수 구하기

-- 실습 7-6
SELECT COUNT(*)
  FROM EMP
 WHERE DEPTNO = 30;

COUNT 함수를 사용하기 급여 개수 구하기(DISTINCT, ALL 사용)

-- 실습 7-7
SELECT COUNT(DISTINCT SAL),
       COUNT(ALL SAL),
       COUNT(SAL) # 옵션을 지정 안 하면 ALL이 기본
  FROM EMP;

COUNT 함수를 사용하여 추가 수당 열 개수 출력하기

-- 실습 7-8
SELECT COUNT(COMM)
  FROM EMP;

COUNT 함수와 IS NOT NULL을 사용하여 추가 수당 열 개수 출력하기

-- 실습 7-9SELECT COUNT(COMM)
  FROM EMP
 WHERE COMM IS NOT NULL;

3) MAX

부서 번호가 10번인 사원들의 최대 급여 출력하기

-- 실습 7-10
SELECT MAX(SAL)
  FROM EMP
 WHERE DEPTNO = 10;

부서 번호가 20번인 사원의 입사일 중 제일 최근 입사일 출력하기

-- 실습 7-12
SELECT MAX(HIREDATE)
  FROM EMP
 WHERE DEPTNO = 20;

부서 번호가 10번인 사원들의 최소 출력 급여 출력하기

-- 실습 7-11
SELECT MIN(SAL)
  FROM EMP
 WHERE DEPTNO = 10;

부서 번호가 20인 사원의 입사일 중 제일 오래된 입사일 출력하기

-- 실습 7-13
SELECT MIN(HIREDATE) # 입사한 연도가 제일 적은 사람이 입사일이 제일 오래된 사람
  FROM EMP
 WHERE DEPTNO = 20;

4) AVG

부서 번호가 30인 사람들의 평균 급여 출력하기

-- 실습 7-14
SELECT AVG(SAL)
  FROM EMP
 WHERE DEPTNO = 30;
-- 실습 7-15
SELECT AVG(DISTINCT SAL)
	FROM EMP
	WHERE DEPTNO = 30;

2. 그룹화와 관련된 함수

ROLLUP, CUBE : 그룹화 데이터의 합계

GROUPING SETS : 지정한 각 열별 그룹화

GROUPING : ROLLUP, CUBE와 함께 사용 (하나)

GROUPING_ID : ROLLUP, CUBE와 함께 사용 (여럿)

LISTAGG : 그룹 데이터 가로 출력

PIVOT, UNPIVOT : 행/열 바꾸어 출력

1) GROUP BY

집합 연산자를 사용하여 각 부서별 평균 급여 출력하기

-- 실습 7-16
SELECT AVG(SAL), '10' AS DEPTNO FROM EMP WHERE DEPTNO = 10
UNION ALL
SELECT AVG(SAL), '20' AS DEPTNO FROM EMP WHERE DEPTNO = 20
UNION ALL
SELECT AVG(SAL), '30' AS DEPTNO FROM EMP WHERE DEPTNO = 30;

GROUP BY를 사용하여 부서별 평균 급여 출력하기

-- 실습 7-17
SELECT DEPTNO, AVG(SAL)
  FROM EMP
GROUP BY DEPTNO ;

부서 번호 및 직책별 평균 급여로 정렬하기

-- 실습 7-18
SELECT DEPTNO, JOB, AVG(SAL)
  FROM EMP
GROUP BY DEPTNO, JOB
ORDER BY DEPTNO, JOB;

GROUP BY절에 없는 열을 SELECT절에 포함했을 경우

-- 실습 7-19
SELECT ENAME, DEPTNO, AVG(SAL)
  FROM EMP
GROUP BY DEPTNO;

2) HAVING

GROUP BY절과 HAVING절을 사용하여 출력하기

-- 실습 7-20
SELECT DEPTNO, JOB, AVG(SAL)
  FROM EMP
GROUP BY DEPTNO, JOB
HAVING AVG(SAL) >= 2000
ORDER BY DEPTNO DESC, JOB ASC;

HAVING절 대신 WHERE절을 잘못 사용했을 경우

-- 실습 7-21
SELECT DEPTNO, JOB, AVG(SAL)
  FROM EMP
 WHERE AVG(SAL) >= 2000
GROUP BY DEPTNO, JOB
ORDER BY DEPTNO, JOB;

# 에러

WHERE절을 사용하지 않고 HAVING절만 사용한 경우

-- 실습 7-22
SELECT DEPTNO, JOB, AVG(SAL)
  FROM EMP
GROUP BY DEPTNO, JOB
HAVING AVG(SAL) >= 2000
ORDER BY DEPTNO, JOB;

WHERE절과 HAVING절을 모두 사용한 경우

-- 실습 7-23
SELECT DEPTNO, JOB, AVG(SAL)
  FROM EMP
 WHERE SAL <= 3000
GROUP BY DEPTNO, JOB
HAVING AVG(SAL) >= 2000
ORDER BY DEPTNO, JOB;

3) ROLLUP

기존 GROUP BY절만 사용한 그룹화

-- 실습 7-24
SELECT DEPTNO, JOB, COUNT(*), MAX(SAL), SUM(SAL), AVG(SAL)
  FROM EMP
GROUP BY DEPTNO, JOB
ORDER BY DEPTNO, JOB;

ROLLUP 함수를 적용한 그룹화

-- 실습 7-25
SELECT DEPTNO, JOB,
       COUNT(*), MAX(SAL),
       SUM(SAL), AVG(SAL)
  FROM EMP
GROUP BY ROLLUP(DEPTNO, JOB);

4) CUBE

CUBE 함수를 적용한 그룹화

-- 실습 7-26
SELECT DEPTNO, JOB, COUNT(*), MAX(SAL), SUM(SAL), AVG(SAL)
  FROM EMP
GROUP BY CUBE(DEPTNO, JOB)
ORDER BY DEPTNO, JOB;

5) ROLLUP VS CUBE

DEPTNO를 먼저 그룹화한 후 ROLLUP 함수에 JOB 지정하기

-- 실습 7-27
SELECT DEPTNO, JOB, COUNT(*)
  FROM EMP
GROUP BY DEPTNO, ROLLUP(JOB);

JOB을 먼저 그룹화한 후 ROLLUP 함수에 DEPTNO 지정하기

-- 실습 7-28
SELECT JOB, DEPTNO,  COUNT(*)
  FROM EMP
GROUP BY JOB, ROLLUP(DEPTNO);

6) GROUPING SETS

GROUPING SETS 함수를 사용하여 열별로 그룹으로 묶어 출력하기

-- 실습 7-29
SELECT DEPTNO, JOB, COUNT(*)
  FROM EMP
GROUP BY GROUPING SETS(DEPTNO, JOB)
ORDER BY DEPTNO, JOB;

7) GROUPING : ROLLUP, CUBE와 함께 사용 (하나)

DEPTNO, JOB열의 그룹화 결과 여부를 GROUPING 함수로 확인하기

-- 실습 7-30
SELECT DEPTNO, JOB, COUNT(*), MAX(SAL), SUM(SAL), AVG(SAL),
       GROUPING(DEPTNO),
       GROUPING(JOB)
  FROM EMP
GROUP BY CUBE(DEPTNO, JOB )
ORDER BY DEPTNO, JOB;

DECODE문으로 GROUPING 함수를 적용하여 결과 표기하기

-- 실습 7-31
SELECT DECODE(GROUPING(DEPTNO), 1, 'ALL_DEPT', DEPTNO) AS DEPTNO,
       DECODE(GROUPING(JOB), 1, 'ALL_JOB', JOB) AS JOB,
       COUNT(*), MAX(SAL), SUM(SAL), AVG(SAL)
  FROM EMP
GROUP BY CUBE(DEPTNO, JOB)
ORDER BY DEPTNO, JOB;

8) GROUPING_ID : ROLLUP, CUBE와 함께 사용 (여럿)

DEPTNO, JOB을 함께 명시한 GROUPING_ID 함수 사용하기

-- 실습 7-32
SELECT DEPTNO, JOB, COUNT(*), SUM(SAL),
       GROUPING(DEPTNO),
       GROUPING(JOB),
       GROUPING_ID(DEPTNO, JOB)
  FROM EMP
GROUP BY CUBE(DEPTNO, JOB)
ORDER BY DEPTNO, JOB;

9) LISTAGG : 그룹 데이터 가로 출력

GROUP BY절로 그룹화하여 부서 번호와 사원 이름 출력하기

-- 실습 7-33
SELECT DEPTNO, ENAME
FROM EMP
GROUP BY DEPTNO, ENAME
ORDER BY DEPTNO, ENAME;

부서별 사원 이름을 나란히 나열하여 출력하기

-- 실습 7-34
SELECT DEPTNO,
       LISTAGG(ENAME, ', ')
       WITHIN GROUP(ORDER BY SAL DESC) AS ENAMES
  FROM EMP
GROUP BY DEPTNO;

10) PIVOT : 행/열 바꾸어 출력

부서별,직책별로 그룹화하여 최고 급여 데이터 출력하기

-- 실습 7-35
SELECT DEPTNO, JOB, MAX(SAL)
  FROM EMP
GROUP BY DEPTNO, JOB
ORDER BY DEPTNO, JOB;

PIVOT 함수를 사용하여 직책별, 부서별 최고 급여를 2차원 표 형태로 출력하기

-- 실습 7-36
SELECT *
  FROM(SELECT DEPTNO, JOB, SAL
         FROM EMP)
PIVOT(MAX(SAL)
      FOR DEPTNO IN (10, 20, 30)
      )
ORDER BY JOB;

PIVOT 함수를 사용하여 부서별,직책별 최고 급여를 2차원 표 형태로 출력하기

-- 실습 7-37
SELECT *
  FROM(SELECT JOB, DEPTNO, SAL
         FROM EMP)
PIVOT(MAX(SAL)
     FOR JOB IN ('CLERK' AS CLERK,
                 'SALESMAN' AS SALESMAN,
                 'PRESIDENT' AS PRESIDENT,
                 ' MG' AS  MG,
                 'ANALYST' AS ANALYST)
     )
ORDER BY DEPTNO;

DECODE문을 활용하여 PIVOT 함수와 같은 출력 구현하기

-- 실습 7-38
SELECT DEPTNO,
       MAX(DECODE(JOB, 'CLERK', SAL)) AS "CLERK",
       MAX(DECODE(JOB, 'SALESMAN', SAL)) AS "SALESMAN",
       MAX(DECODE(JOB, 'PRESIDENT', SAL)) AS "PRESIDENT",
       MAX(DECODE(JOB, ' MG', SAL)) AS " MG",
       MAX(DECODE(JOB, 'ANALYST', SAL)) AS "ANALYST"
  FROM EMP
GROUP BY DEPTNO
ORDER BY DEPTNO;

11) UNPIVOT

UNPIVOT 함수를 사용하여 열로 구분된 그룹을 행으로 출력하기

-- 실습 7-39
SELECT *
  FROM(SELECT DEPTNO,
              MAX(DECODE(JOB, 'CLERK' , SAL)) AS "CLERK",
              MAX(DECODE(JOB, 'SALESMAN' , SAL)) AS "SALESMAN",
              MAX(DECODE(JOB, 'PRESIDENT', SAL)) AS "PRESIDENT",
              MAX(DECODE(JOB, ' MG' , SAL)) AS " MG",
              MAX(DECODE(JOB, 'ANALYST' , SAL)) AS "ANALYST"
         FROM EMP
       GROUP BY DEPTNO
       ORDER BY DEPTNO)
UNPIVOT(
   SAL FOR JOB IN (CLERK, SALESMAN, PRESIDENT,  MG,ANALYST))
ORDER BY DEPTNO, JOB;

SELECT *
    FROM EMP NATURAL JOIN DEPT;

'SQL > 개념' 카테고리의 다른 글

05. 서브쿼리  (0) 2023.05.03
04. 조인  (0) 2023.05.03
02. 오라클 함수  (0) 2023.05.03
01. SQL 개념과 기초  (1) 2023.05.02
00. 데이터 모델링  (0) 2023.05.02