1μ₯μμλ 본격μ μΌλ‘ μμνκΈ° μ μ μ΅ν°λ§μ΄μ κ° SQLμ μ΄λ»κ² μ²λ¦¬νλμ§, μλ² νλ‘μΈμ€λ λ°μ΄ν°λ₯Ό μ΄λ»κ² μ½κ³ μ μ₯νλμ§λ₯Ό μμ보μ.
1. SQL νμ±κ³Ό μ΅μ ν
β³οΈ SQL νμ±
- νμ± νΈλ¦¬ μμ± : SQLλ¬Έμ μ΄λ£¨λ κ°λ³ κ΅¬μ± μμλ₯Ό λΆμν΄μ νμ± νΈλ¦¬ μμ±
- Syntax μ²΄ν¬ : λ¬Έλ²μ μ€λ₯ νμΈ π μ¬μ©ν μ μλ ν€μλ μ¬μ© λλ μμ, λλ½λ ν€μλ νμΈ
- Semantic μ²΄ν¬ : μλ―Έμ μ€λ₯ νμΈ π μ‘΄μ¬νμ§ μλ ν μ΄λΈ λλ μ»¬λΌ μ¬μ©μ¬λΆ, μ¬μ©ν μ€λΈμ νΈμ λν κΆν νμΈ
β³οΈ SQL μ΅μ ν
νμ± λ€μ λ¨κ³λ‘μ DBMS λ΄λΆμμ νλ‘μμ λ₯Ό μμ±νκ³ μ»΄νμΌν΄μ μ€ν κ°λ₯ν μνλ‘ λ§λλ μ κ³Όμ π μ΅ν°λ§μ΄μ κ° μν μν
- μ΅ν°λ§μ΄μ λ 미리 μμ§ν μμ€ν λ° μ€λΈμ νΈ ν΅κ³μ 보λ₯Ό λ°νμΌλ‘ λ€μν μ€ν κ²½λ‘ μμ±ν΄μ λΉκ΅ν ν κ°μ₯ ν¨μ¨μ μΈ νλ μ ν
- λ°μ΄ν°λ² μ΄μ€ μ±λ₯μ κ²°μ νλ κ°μ₯ ν΅μ¬μ μΈ μμ§
β³οΈ λ‘μ° μμ€ μμ±
- SQL μ΅ν°λ§μ΄μ κ° μ νν μ€ν κ²½λ‘λ₯Ό μ€μ μ€ν κ°λ₯ν μ½λ λλ νλ‘μμ ννλ‘ ν¬λ§·ν
- λ‘μ° μμ€ μμ±κΈ° (Row-Source Generator)κ° μν μν
SQL μ΅ν°λ§μ΄μ
μ¬μ©μκ° μνλ μμ μ κ°μ₯ ν¨μ¨μ μΌλ‘ μνν μ μλ μ΅μ μ λ°μ΄ν° μ‘μΈμ€ κ²½λ‘λ₯Ό μ νν΄ μ£Όλ DBMS ν΅μ¬ μμ§
- μ¬μ©μλ‘λΆν° λ°μ 쿼리λ₯Ό μννλ λ° νλ³΄κ΅°μ΄ λ λ§ν μ€ν κ³νλ€μ μ°Ύμλ
- λ°μ΄ν° λμ λ리μ 미리 μμ§ν΄ λ μ€λΈμ νΈ ν΅κ³ λ° μμ€ν ν΅κ³μ 보λ₯Ό μ΄μ©ν΄ κ° μ€ν κ³νμ μμ λΉμ© μ°μ
- μ΅μ λΉμ©μ λνλ΄λ μ€ν κ³ν μ ν
μ€ν κ³νκ³Ό λΉμ©
β³οΈ μ€ν κ³ν (Execution plan)
ID OPERATION OBJECT NAME CARD COST
-------------------------------------------------------------------
0 SELECT STATEMENT 1000 500
1 NESTED LOOPS 1000 400
2 NESTED LOOPS 1000 300
3 TABLE ACCESS FULL EMPLOYEES 1000 200
4 TABLE ACCESS FULL DEPARTMENTS 50 10
5 SORT AGGREGATE 1 5
6 TABLE ACCESS FULL SALARIES 10 50
7 SORT ORDER BY FETCH FIRST ROW ONLY 1 8
8 INDEX RANGE SCAN SALARIES_IDX 10 5
- SQL μ΅ν°λ§μ΄μ κ° μμ±ν μ²λ¦¬ μ μ°¨λ₯Ό μ¬μ©μκ° νμΈν μ μκ² νΈλ¦¬ κ΅¬μ‘°λ‘ νν
- ν μ΄λΈμ μ€μΊνλμ§, μΈλ±μ€λ₯Ό μ€μΊνλμ§ λ±μ νμΈ
- μ΅ν°λ§μ΄μ κ° νΉμ μ€νκ³νμ μ ννλ κ·Όκ±°λ ? π λΉμ©μΌλ‘ μ ν !
SET AUTOTRACE TRACEONLY EXPLAIN;
SELECT * FROM t
WHERE deptno = 10;
and no = 1;
Execution Plan
----------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost |
----------------------------------------------------------
| 0 | SELECT STATEMENT | | 3 | 123 | 2 |
| 1 | INDEX RANGE SCAN | IDX_EMP_DEPTNO | 3 | 123 | 2 |
----------------------------------------------------------
πΉ λΉμ© (Cost) μ΄λ ?
- 쿼리λ₯Ό μννλ λμ λ°μν κ²μΌλ‘ μμνλ I/O νμ λλ μμ μμ μκ°μ νν
- μ€μΈ‘μΉκ° μλ μμμΉμ΄λ―λ‘ μ€μ μ€νν λ λ°μνλ I/O λλ μκ°κ³Ό λ§μ μ°¨μ΄ λ°μ κ°λ₯
- λΉμ©μ λν μ νν μλ―Έλ μΆνμ μ 리 ...!
μ΅ν°λ§μ΄μ ννΈ
SQLμ΄ λ³΅μ‘ν μλ‘ μ€μν κ°λ₯μ±λ ν¬κΈ° λλ¬Έμ ν΅κ³ μ 보μ λ΄μ μ μλ λ°μ΄ν° λλ μ 무 νΉμ±μ νμ©ν΄ κ°λ°μκ° μ§μ λ ν¨μ¨μ μΈ μ‘μΈμ€ κ²½λ‘λ₯Ό μ°ΎμλΌ μ μλ€. μ΄λ΄ λ μ΅ν°λ§μ΄μ ννΈλ₯Ό μ΄μ©ν΄ λ°μ΄ν° μ‘μΈμ€ κ²½λ‘λ₯Ό λ°κΏ μ μλ€.
π ννΈ μ¬μ©λ²μ μ£Όμ κΈ°νΈμ '+'λ₯Ό λΆμ΄λ©΄ λ¨
SELECT /*+ INDEX(emp idx_emp_deptno) */ *
FROM emp
WHERE deptno = 10;
πΉ ννΈ μ¬μ© μ£Όμμ¬ν
- ννΈ μμ μΈμλ₯Ό λμ΄ν λλ ',' (μ½€λ§)λ₯Ό μ¬μ©ν μ μμ§λ§, ννΈμ ννΈ μ¬μ΄μ μ¬μ©νλ©΄ μλ¨
/*+ INDEX(A A_X01) INDEX(B, B_X03) */ -> λͺ¨λ μ ν¨
/*+ INDEX(C), FULL(D) */ -> 첫 λ²μ§Έ ννΈλ§ μ ν¨
- ν μ΄λΈμ μ§μ ν λ μ€ν€λ§λͺ κΉμ§ λͺ μνλ©΄ μλ¨
SELECT /*+ FULL(SCOTT.EMP) */ -> 무ν¨
FROM EMP
- FROM μ ν μ΄λΈλͺ μμ ALIASλ₯Ό μ§μ νλ€λ©΄ ννΈμλ λ°λμ ALIAS μ¬μ©
SELECT /*+ FULL(EMP) */ -> 무ν¨
FROM EMP E
πΉ μ΅ν°λ§μ΄μ κ° μμ¨ λλ κ°μ μ μΌλ‘ μ€νν μ μκ² λ§λ€κΈ°
SELECT /*+ INDEX(A (μ£Όλ¬ΈμΌμ)) */
A.μ£Όλ¬Έλ²νΈ, A.μ£Όλ¬ΈκΈμ‘, B.κ³ κ°λͺ
, B.μ°λ½μ², B.μ£Όμ
FROM μ£Όλ¬Έ A, κ³ κ° B
WHERE A.μ£Όλ¬ΈμΌμ = :ORD_DT
AND A.κ³ κ°ID = B.κ³ κ°ID
- μ£Όλ¬Έ ν μ΄λΈμ μ‘μΈμ€ν λ μ£Όλ¬ΈμΌμ 컬λΌμ΄ μ λμΈ μΈλ±μ€λ₯Ό μ¬μ©νλλ‘ ννΈλ‘ μ§μ
- μ‘°μΈ λ°©μκ³Ό μμ, κ³ κ° ν μ΄λΈ μ‘μΈμ€ λ°©μμ μ΅ν°λ§μ΄μ κ° μμμ νλ¨νλλ‘ λ¨κ²¨λ
SELECT /*+ LEADING(A) USE_NL(B) INDEX(A (μ£Όλ¬ΈμΌμ)) INDEX(B κ³ κ°_PK) */
A.μ£Όλ¬Έλ²νΈ, A.μ£Όλ¬ΈκΈμ‘, B.κ³ κ°λͺ
, B.μ°λ½μ², B.μ£Όμ
FROM μ£Όλ¬Έ A, κ³ κ° B
WHERE A.μ£Όλ¬ΈμΌμ = :ORD_DT
AND A.κ³ κ°ID = B.κ³ κ°ID
- 첫 λ²μ§Έ SQLκ³Ό λ¬λ¦¬ μ λ λ€λ₯Έ λ°©μμ μ ννμ§ λͺ»νλλ‘ ννΈλ₯Ό λΉνμμ΄ μ§μ
- LEADING(A) : A ν μ΄λΈμ 첫 λ²μ§Έλ‘ μ²λ¦¬ π μ‘°μΈ μμ μ§μ
- USE_NL(B) : Aμ Bλ₯Ό μ€μ²© 루ν λ°©μμΌλ‘ μ‘°μΈνλλ‘ μ§μ
π A ν μ΄λΈμ κ° νμ λν΄ B ν μ΄λΈμ κ²μ (B ν μ΄λΈμ΄ λ μκ±°λ μΈλ±μ€λ₯Ό νμ©ν μ μμ λ μ¬μ©)
β¨ μμ£Ό μ¬μ©νλ ννΈλ€μ μ΄νμ μ°¨κ·Όμ°¨κ·Ό μ 리