SQLD/SQL 기본과 활용
SQL) GROUP BY 절, HAVING 절, ORDER BY절, SELECT 문장 실행 순서
DevPing9_
2020. 8. 20. 17:13
# 실행 순서 : FROM -> WHERE -> GROUP BY -> HAVING -> SELECT -> ORDER BY
(옵티마이저가 SYNTAX, SEMANTIC 에러를 점검하는 논리적 순서)
(물리적 순서는 실행계획에 의해 정해짐)
1. GROUP BY절
# GROUP BY 절은 FROM, WHERE절 뒤에 위치하며, 데이터들을 소그룹에 대한 항목별로 통계 정보를 얻을 때 추가로 사용된다.
/*
SELECT [DISTINCT] COL1 [ALIAS]
FROM TAB1
[WHERE condition1]
[GROUP BY exp1]
[HAVING condition2]
[ORDER BY exp2 [ASC | DESC]];
*/
# 집계함수는 WHERE 절에 올 수 없다
# 실행순서 : FROM -> WHERE -> GROUP BY -> HAVING -> SELECT -> ORDER BY
# HAVING 절은 GROUP BY 절의 조건을 담음
# 즉, WHERE에서 걸러진 GROUP을 HAVING으로 다시 거르는 작업
# 추가) GROUP BY 절에는 SELECT 절에서 정의된 ALIAS를 사용할 수 없다
SQL> SELECT POSITION
,COUNT (*) AS TOTAL
,COUNT (NFS) AS NOT_FORSALE
,MAX (HEIGHT) AS MAX_HEIGHT
,MIN (HEIGHT) AS MIN_HEIGHT
,ROUND (AVG (HEIGHT), 2) AS AVG_HEIGHT
FROM PLAYER
GROUP BY POSITION;
# 실행결과 (GROUP BY에 의해 묶인 그룹별로 집계함수가 작동하는 것을 볼 수 있음)
POSITION TOTAL NOT_FORSALE MAX_HEIGHT MIN_HEIGHT AVG_HEIGHT
------------------------------------------------------------------------------------
3 0
GK 46 11 197 182 188.82
DF 177 10 190 176 184.23
FW 120 6 194 167 176.69
MF 185 3 188 167 178.88
2. HAVING 절
- GROUP BY 연산 후 HAVING절에 의해 필터링 됨
- 왠만하면 WHERE 절에서 필요한 데이터만 추출하여 GROUP BY 연산을 하는 것이 효율적임
- 그룹별 집계함수 적용은 HAVING절을 이용해야 함. (WHERE절에서 사용 불가능, 오류발생)
/*
SELECT [DISTINCT] COL1 [ALIAS]
FROM TAB1
[WHERE condition1]
[GROUP BY exp1]
[HAVING condition2]
[ORDER BY exp2 [ASC | DESC]];
*/
SQL> SELECT TEAM_NAME, COUNT(*) AS TOTAL
FROM PLAYER
WHERE TEAM_NAME IN ('삼성버거킹', '롯데맥도날드')
GROUP BY TEAM_NAME;
SQL> SELECT TEAM_NAME, COUNT(*) AS TOTAL
FROM PLAYER
GROUP BY TEAM_NAME
HAVING TEAM_NAME IN ('삼성버거킹', '롯데맥도날드');
# 실행결과 (결과는 같으나 GROUP BY연산의 결과 데이터들의 갯수가 차이가 남)
TEAM_NAME TOTAL
-------------------------
삼성버거킹 85
롯데맥도날드 70
3. ORDER BY절
- DEFAULT 정렬값은 오름차순(ASC)
- 날짜형 데이터 타입은 과거가 작은 값
- NULL값은 Oracle에서는 가장 큰 값, SQL Server에서는 가장 작은 값
- SELECT절에서 언급되지 않은 다른컬럼 사용가능 (행 단위 모든칼럼 단위 데이터 사용가능)
/*
SELECT [DISTINCT] COL1 [ALIAS]
FROM TAB1
[WHERE condition1]
[GROUP BY exp1]
[HAVING condition2]
[ORDER BY exp2 [ASC | DESC]];
*/
SQL> SELECT TEAM_NAME, COUNT(*) AS TOTAL
FROM PLAYER
WHERE TEAM_NAME IN ('삼성버거킹', '롯데맥도날드')
GROUP BY TEAM_NAME;
SQL> SELECT TEAM_NAME, COUNT(*) AS TOTAL
FROM PLAYER
GROUP BY TEAM_NAME
HAVING TEAM_NAME IN ('삼성버거킹', '롯데맥도날드');
# 실행결과 (결과는 같으나 GROUP BY연산의 결과 데이터들의 갯수가 차이가 남)
TEAM_NAME TOTAL
-------------------------
삼성버거킹 85
롯데맥도날드 70
728x90