Oracle SQL Tuning

Huisuยท2025๋…„ 8์›” 19์ผ

ETC

๋ชฉ๋ก ๋ณด๊ธฐ
12/12
post-thumbnail

๐Ÿ’กSQL TUNING
DB time์ด๋ผ๊ณ ๋„ ๋ถˆ๋ฆฌ๋Š” ์ฒ˜๋ฆฌ ์‹œ๊ฐ„์€ SQL ์‹คํ–‰ ์†๋„ + ๋Œ€๊ธฐ ์‹œ๊ฐ„์œผ๋กœ ๊ตฌ์„ฑ๋œ๋‹ค. ์ด๋•Œ, SQL ์‹คํ–‰ ์†๋„๋ฅผ ์ค„์—ฌ ์ „์ฒด์ ์ธ ์ฒ˜๋ฆฌ ์‹œ๊ฐ„์„ ์ค„์ด๋Š” ๊ณผ์ •์„ SQL TUNING์ด๋ผ๊ณ  ํ•œ๋‹ค.

SQL ์ฒ˜๋ฆฌ ๊ณผ์ •

ORACLE DATABASE

ORACLE DATABASE

์˜ค๋ผํด ๋ฐ์ดํ„ฐ๋ฒ ์ด์Šค ์„œ๋ฒ„๋Š” ์ธ์Šคํ„ด์Šค์™€ ๋ฐ์ดํ„ฐ๋ฒ ์ด์Šค๋กœ ๊ตฌ์„ฑ๋˜์–ด ์žˆ๋‹ค.

DATABASE

์˜ค๋ผํด์ด ์‚ฌ์šฉํ•˜๋Š” 3๊ฐ€์ง€ ํƒ€์ž…์˜ ๋ฌผ๋ฆฌ์  ์ €์žฅ ํŒŒ์ผ์ด ์žˆ๋‹ค.

  • Data: ์œ ์ € ๋ฐ์ดํ„ฐ ์ €์žฅ, ์—ฌ๊ธฐ์— ์žˆ๋Š” ๋กœ์šฐ๋ฐ์ดํ„ฐ๋ฅผ ์‚ฌ์šฉ, ํ•˜๋‚˜๋กœ ํ•ด๊ฒฐ๋˜์ง€ ์•Š์•„ ์—ฌ๋Ÿฌ ๊ฐœ๋กœ ๊ตฌ์ถ•ํ•  ์ˆ˜ ์žˆ์Œ
  • Redo: ๋ณต๊ตฌ์— ์‚ฌ์šฉํ•˜๊ธฐ ์œ„ํ•œ ๋กœ๊ทธ
  • Control: Physical Structure ์ •๋ณด (Data File List, ๋™๊ธฐํ™” ์ •๋ณด, DB Structure), ์ฐพ๊ณ ์ž ํ•˜๋Š” ๋ฐ์ดํ„ฐ๊ฐ€ ์–ด๋–ค Data ํŒŒ์ผ์— ์žˆ๋Š”์ง€ ๋“ฑ๋“ฑ์˜ ์œ„์น˜ ์ •๋ณด ์ €์žฅ, ๋™๊ธฐํ™” ์ •๋ณด
    • ์ •๋ณด ์ž์ฒด์˜ ์–‘์€ ์ž‘์œผ๋‚˜ ์†์‹ค๋  ๊ฒฝ์šฐ ๋ฐ์ดํ„ฐ๋ฅผ ์ฐพ์ง€ ๋ชปํ•˜๋Š” ๊ฒฝ์šฐ๊ฐ€ ๋งŽ์Œ
    • ๋”ฐ๋ผ์„œ ์žฅ์•  ๋Œ€์‘์„ ์œ„ํ•ด ๋ฏธ๋Ÿฌ๋ง์˜ ๊ฐœ๋…์œผ๋กœ ์—ฌ๋Ÿฌ ๊ฐœ๋ฅผ ๋งŒ๋“ค์–ด์„œ ์•ˆ์ •์  ์šด์˜

Instance

์˜ค๋ผํด ์ธ์Šคํ„ด์Šค๋Š” System Global Aread๋ผ๋Š” ๋ฉ”๋ชจ๋ฆฌ ๊ตฌ์กฐ์™€ ์ธ์Šคํ„ด์Šค ์‹คํ–‰๊ณผ ๊ด€๋ จ๋œ ๋Œ€ใ…”๋ถ€๋ถ„์˜ ์ž‘์—…์„ ์ฒ˜๋ฆฌํ•˜๋Š” ๋ฐฑ๊ทธ๋ผ์šด๋“œ ํ”„๋กœ์„ธ์Šค๋กœ ๊ตฌ์„ฑ๋œ๋‹ค. ๋ฐฑ๊ทธ๋ผ์šด๋“œ ํ”„๋กœ์„ธ์Šค์˜ ์˜ˆ์‹œ๋กœ๋Š” Shared Pool, Streams Pool, Large Pool, Java Pool, Database Buffer Cache, Redo Log Buffer ๋“ฑ์ด ์žˆ๋‹ค.

์˜ค๋ผํด์ด ๋œฐ ๋•Œ OS์—๊ฒŒ ๋ฉ”๋ชจ๋ฆฌ ํ• ๋‹น์„ ์š”๊ตฌํ•ด SGA์— ํ•ด๋‹นํ•˜๋Š” ๋ฉ”๋ชจ๋ฆฌ๋ฅผ ํ™•๋ณดํ•˜๊ฒŒ ๋œ๋‹ค. ์ดํ›„ ๋„์›Œ์•ผ ํ•˜๋Š” ๋ฐฑ๊ทธ๋ผ์šด๋“œ ํ”„๋กœ์„ธ์Šค๊นŒ์ง€ ๋„์šฐ๋Š” ๊ฒƒ์ด STARTUP ๋ช…๋ น์–ด์˜ ์—ญํ• ์ด๋‹ค.

์ดํ›„์— SELECT, UPDATE ๋“ฑ์ด ๊ฐ€๋Šฅํ•œ๋ฐ, ๊ทธ ๋ง์€ ๋ฐฑ๊ทธ๋ผ์šด๋“œ ํ”„๋กœ์„ธ์Šค๊ฐ€ ๋ช…๋ น์–ด ์ฒ˜๋ฆฌ๋ฅผ ์œ„ํ•ด ๋ฐ˜๋“œ์‹œ ํ•„์š”ํ•˜๋‹ค๋Š” ๋œป์ด๋‹ค.

์—ฌ๋Ÿฌ ๋ฐฑ๊ทธ๋ผ์šด๋“œ ํ”„๋กœ์„ธ์Šค ์ค‘์—์„œ Shared Pool, Database Buffer Cache, Redo Log Buffer๋Š” ํ•„์ˆ˜์ ์œผ๋กœ ์‹คํ–‰๋œ๋‹ค. ์ฆ‰, ์ด ์„ธ ๊ฐœ์˜ ํ”„๋กœ์„ธ์Šค๋Š” ๋ฌด์กฐ๊ฑด ์žˆ์–ด์•ผ ๋ช…๋ น์–ด ์‹คํ–‰ํ•  ์ค€๋น„๊ฐ€ ๊ฐ€๋Šฅํ•ด์ง„๋‹ค๋Š” ๊ฒƒ์ด๋‹ค.

SELECT ๋ช…๋ น์–ด ์ฒ˜๋ฆฌ

DEDICATED SERVER

  • ๊ฐœ๋ฐœ์ž ํˆด์—์„œ User Process ๋งŒ๋“ค๊ธฐ
  • ์˜ค๋ผํด ์„œ๋ฒ„์— Username, Password ์ „๋‹ฌํ•˜๋ฉด ์˜ค๋ผํด ์„œ๋ฒ„์—์„œ ์„œ๋ฒ„ ํ”„๋กœ์„ธ์Šค ์ƒ์„ฑ
  • ์ธ์ฆ ์ ˆ์ฐจ ์‹คํ–‰ ํ›„ ์„ธ์…˜ ์‹œ์ž‘ โ†’ ๋ช…๋ น์–ด ์‹คํ–‰ ์ค€๋น„ ์™„๋ฃŒ
  • ์œ ์ €์™€ ์„œ๋ฒ„ ํ”„๋กœ์„ธ์Šค๊ฐ€ 1:1๋กœ ๋งค์นญ๋˜์–ด ์žˆ์Œ
  • ์œ ์ € ํ”„๋กœ์„ธ์Šค๊ฐ€ Connection ๋Š์œผ๋ฉด ์„œ๋ฒ„ ํ”„๋กœ์„ธ์Šค๋„ ํ•จ๊ป˜ ์‚ฌ๋ผ์ง
  • ์„œ๋ฒ„ ํ”„๋กœ์„ธ์Šค๋Š” STARTUP ํ•  ๋•Œ ๋œจ๋Š” ๊ฒƒ์ด ์•„๋‹ˆ๋ผ, ์œ ์ €๊ฐ€ ๋กœ๊ทธ์ธํ•  ๊ฒฝ์šฐ์— ์ƒ์„ฑ
  • ์„œ๋ฒ„ ํ”„๋กœ์„ธ์Šค = ์˜ตํ‹ฐ๋งˆ์ด์ €

PARSE

  • ์˜ตํ‹ฐ๋งˆ์ด์ €๊ฐ€ ์•Œ์•„๋“ค์„ ์ˆ˜ ์žˆ๋Š” P-Code๋กœ ๋ณ€ํ™˜ํ•˜๋Š” ๊ณผ์ •
  • Syntax Check: ๋ฌธ๋ฒ•์  ์˜ค๋ฅ˜ ํ™•์ธ
  • Semantic Check: ์˜๋ฏธ์ƒ ์˜ค๋ฅ˜ ํ™•์ธ (ํ…Œ์ด๋ธ”์ด ์‹ค์ œ๋กœ ์žˆ๋Š”์ง€, ๊ถŒํ•œ์ด ์žˆ๋Š”์ง€)
  • Shared Pool์— ์ž‘์„ฑ๋œ Shared SQL Area๊ฐ€ ์žˆ๋Š”์ง€ ๊ฒ€์ƒ‰
    • ์žˆ์œผ๋ฉด ์‹คํ–‰ (Soft Parse)
  • ์ˆ˜ํ–‰ ๊ณ„ํš, Row Source๋ฅผ ์ƒ์„ฑํ•˜๊ณ  Shared SQL Area๊ตฌ์กฐ๋กœ ๋งŒ๋“ค์–ด (Hard Parse) Shared Pool์— ์ €์žฅ
    • ํ•ด๋‹น ๋ช…๋ น์–ด๋ž‘ ๋˜‘๊ฐ™์€ ๋ช…๋ น์„ ๋‹ค์‹œ ์ˆ˜ํ–‰ํ•˜๋ ค๊ณ  ํ•  ๋•Œ ์ด๋ฏธ ํŒŒ์‹ฑํ•ด ๋‘” ์ •๋ณด ๊ทธ๋Œ€๋กœ ์žฌ์‚ฌ์šฉํ•˜๊ธฐ ์œ„ํ•ด ์ €์žฅ
    • ๋‹ค๋ฅธ ์„ธ์…˜์ด ์™€๋„ ๊ฐ™์€ Shared Pool ์˜์—ญ ๋ฉ”๋ชจ๋ฆฌ๋ฅผ ์‚ฌ์šฉํ•˜๊ธฐ ๋•Œ๋ฌธ์—, ์—ฌ๋Ÿฌ ์„ธ์…˜์ด ํ•จ๊ป˜ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ์Œ
  • TUNING POINT: Soft Parse๋ฅผ ์ž์ฃผ ํ™œ์šฉํ•  ์ˆ˜ ์žˆ๋„๋ก ํ•˜๊ธฐ
    • ๋™์ผํ•œ ๋ช…๋ น์–ด ์ˆ˜ํ–‰ (๋Œ€์†Œ๋ฌธ์ž ์ผ์น˜, ๊ณต๋ฐฑ๋ฌธ์ž ์ผ์น˜, ๋ฐ”์ธ๋“œ ๋ณ€์ˆ˜ ํ™œ์šฉ)
    • cursor_sharing=force ๋“ฑ์˜ ์˜ต์…˜์„ ๋‘ฌ์„œ ๋ฐ”์ธ๋“œ๋ณ€์ˆ˜๋ฅผ ์‚ฌ์šฉํ•˜์ง€ ์•Š์•„๋„ ๋™์ผํ•œ ํšจ๊ณผ๋ฅผ ๋ณผ ์ˆ˜ ์žˆ๋„๋ก ์„ค์ • ๊ฐ€๋Šฅ (์ „์ฒด ์‹œ์Šคํ…œ ๋ ˆ๋ฒจ์—์„œ๋Š” ์˜คํžˆ๋ ค ์„ฑ๋Šฅ ์ €ํ•˜๊ฐ€ ์ผ์–ด๋‚  ์ˆ˜ ์žˆ์–ด์„œ ๊ถŒํ•˜์ง€ ์•Š๊ณ  ํ•ด๋‹น ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜ ์„ธ์…˜ ์ •๋„์—์„œ๋งŒ ์‚ฌ์šฉ ์ถ”์ฒœ)

EXECUTE

  • Row Source๋ฅผ ์ˆ˜ํ–‰ํ•˜์—ฌ Data๊ฐ€ ์œ„์น˜ํ•œ Block์˜ ์ฃผ์†Œ๋ฅผ ์•Œ์•„๋ƒ„
  • DB Buffer Cache์—์„œ ๊ฒ€์ƒ‰ํ•˜๋ ค๋Š” Block์ด ์žˆ๋Š”์ง€๋ฅผ ๊ฒ€์ƒ‰ํ•ด์„œ ์žˆ์œผ๋ฉด ํ•„์š”ํ•œ ํ–‰์„ ์ฝ๊ณ  (Logical Read) Fetch ๋‹จ๊ณ„๋ฅผ ์ˆ˜ํ–‰
  • ์•Œ์•„๋‚ธ ์ฃผ์†Œ๋กœ Datafile์˜ Block์„ ์ฝ์–ด DB Buffer Cache์— ์ €์žฅ (Physical Read) ํ›„ DB Buffer Cache์— ์ €์žฅ๋œ Block ๋‚ด์˜ ํ•„์š”ํ•œ ํ–‰์„ ์ฝ์–ด์˜ด (Logical Read)
  • DB Buffer Cache ์—ญ์‹œ SGA ์˜์—ญ์— ์ €์žฅ๋˜๊ธฐ ๋•Œ๋ฌธ์— ์—ฌ๋Ÿฌ ์„ธ์…˜์ด ํ•จ๊ป˜ ๊ณต์œ  ๊ฐ€๋Šฅ
  • TUNING POINT: Logical Read๋ฅผ ์ž์ฃผ ํ™œ์šฉํ•  ์ˆ˜ ์žˆ๋„๋ก ํ•˜๊ธฐ
    • ๋žœ๋ค์œผ๋กœ ์‹คํ–‰๋˜๊ธฐ ๋•Œ๋ฌธ์— Logical Read๋งŒ ์ค„์ผ ์ˆ˜ ์žˆ๋Š” ํŠœ๋‹์€ ์—†์Œ
    • ๋”ฐ๋ผ์„œ ๊ทธ๋ƒฅ Total I/O๋ฅผ ์ค„์—ฌ์„œ Logical / Physical์„ ๋ชจ๋‘ ์ค„์ด๋Š” ๋ฐฉ์‹์œผ๋กœ ์ˆ˜ํ–‰

FETCH

  • SELECT ๋ช…๋ น์—๋งŒ ์žˆ๋Š” ์ฒ˜๋ฆฌ ๋‹จ๊ณ„ (SELECT๋งŒ ๊ฒฐ๊ณผ๋ฅผ ๋ณด์—ฌ ์ฃผ๊ธฐ ๋•Œ๋ฌธ)
  • ์„œ๋ฒ„ ํ”„๋กœ์„ธ์Šค (์„ธ์…˜ ํ•˜๋‚˜) ํ˜ผ์ž ์“ฐ๋Š” ๋ฉ”๋ชจ๋ฆฌ์ธ PGA๋ฅผ ํ™•๋ณดํ•˜๊ณ  ์žˆ๋Š”๋ฐ, ๊ทธ์ค‘ Cursor Stack์ด๋ผ๋Š” ์ „์šฉ ๋ฉ”๋ชจ๋ฆฌ์— ๊ฐ€์ ธ๋‹ค ๋†“๋Š” ๊ฒƒ๊นŒ์ง€๊ฐ€ Excure ๋‹จ๊ณ„์ด๊ณ , ์ด๋ฅผ ์œ ์ € ํ”„๋กœ์„ธ์Šค ๋ฉ”๋ชจ๋ฆฌ์— ์ „๋‹ฌํ•ด ์คŒ
    • ๋งŒ์•ฝ ์œ ์ €๊ฐ€ 50๊ฐœ์˜ Fetch Array Size๋ฅผ ๊ฐ€์กŒ์„ ๊ฒฝ์šฐ 100๊ฐœ์˜ ๊ฒฐ๊ณผ๋ฅผ ๊ฐ€์ ธ์•ผ ํ•  ๋•Œ ๋‘ ๋ฒˆ ์ „๋‹ฌํ•ด ์ค˜์•ผ ํ•  ๊ฒฝ์šฐ๊ฐ€ ์žˆ์Œ
    • 50๊ฐœ๋ฅผ ์ฝ๊ณ  ๋˜์ง€๊ณ , 50๊ฐœ๋ฅผ ์ฝ๊ณ  ๋˜์ง€๊ณ  ์‹์œผ๋กœ ์ง„ํ–‰ (ํ•œ ๋ฒˆ์— ์ฝ์–ด์˜จ ๋’ค ์ž˜๋ผ์„œ ๋ณด๋‚ด ์ฃผ์ง€ ์•Š์Œ), ์ผ๋‹จ 50๊ฐœ ๋จผ์ € ์ฝ์–ด์„œ ๋˜์ง€๋Š” ๋ฐฉ์‹ โ†’ ๋ถ€๋ถ„ ๋ฒ”์œ„ ์ฒ˜๋ฆฌ
  • User Process์— ๊ฒฐ๊ณผ ํ–‰์„ ์ „๋‹ฌ

Database Buffer Cache

Database Buffer Cache

์‚ฌ์šฉ์ž๊ฐ€ ์š”์ฒญํ•œ SQL ๋ฌธ์žฅ์„ ์ฒ˜๋ฆฌํ•  ๋•Œ, EXECUTE ๋‹จ๊ณ„์—์„œ ์‚ฌ์šฉํ•˜๋Š” ๋ฉ”๋ชจ๋ฆฌ์ด๋‹ค. ์˜ค๋ผํด ์„œ๋ฒ„๊ฐ€ ๊ฐ€์žฅ ์ตœ๊ทผ์— ์ฝ๊ฑฐ๋‚˜ ๋ณ€๊ฒฝํ•˜๊ธฐ ์œ„ํ•ด ์•ก์„ธ์Šคํ–ˆ๋˜ ๋ฐ์ดํ„ฐ ๋ธ”๋ก์˜ ๋ณต์‚ฌ๋ณธ์„ ์ €์žฅํ•˜๋Š” ๋ฉ”๋ชจ๋ฆฌ์ด๋‹ค. ๋ธ”๋ก์˜ ๋ณต์‚ฌ๋ณธ์„ ๋ฉ”๋ชจ๋ฆฌ์— ์ €์žฅํ•ด ๋‘๋ฉด ๋‹ค์Œ ๋ฒˆ์— ํ•ด๋‹น ๋ธ”๋ก ์š”์ฒญ ์‹œ์— ๋””์Šคํฌ I/O๋ฅผ ํ•˜์ง€ ์•Š๊ณ  ๋ฉ”๋ชจ๋ฆฌ์—์„œ ๋ฐ”๋กœ ์ฝ๊ฒŒ ๋˜์–ด ์‘๋‹ต ์†๋„๊ฐ€ ๋นจ๋ผ์ง„๋‹ค. DB_CACHE_SIZE ํŒŒ๋ผ๋ฏธํ„ฐ๋ฅผ ํ†ตํ•ด ํฌ๊ธฐ๋ฅผ ์กฐ์ •ํ•œ๋‹ค.

๋…ผ๋ฆฌ์  I/O, ๋ฌผ๋ฆฌ์  I/O

  • ๋…ผ๋ฆฌ์  I/O
    • SQL์„ ์ฒ˜๋ฆฌํ•˜๋Š” ๊ณผ์ •์—์„œ ๋ฐœ์ƒํ•œ ์ด ๋ธ”๋ก I/O
    • Memotu I/O + Direct Path I/O
    • SQL ํŠœ๋‹์‹œ ๋ชฉํ‘œ๋Š” ๋…ผ๋ฆฌ์  I/O๋ฅผ ์ค„์ด๋Š” ๊ฒƒ
  • ๋ฌผ๋ฆฌ์  I/O
    • ๋””์Šคํฌ์—์„œ ๋ฐœ์ƒํ•œ ์ด ๋ธ”๋ก I/O
    • ๋…ผ๋ฆฌ์  I/O ์ค‘ ์ผ๋ถ€
    • ์„œ๋ฒ„ ์‹œ์Šคํ…œ ์ƒํ™ฉ์— ์˜ํ•ด ๊ฒฐ์ •๋˜๋ฉฐ ๋…ผ๋ฆฌ์  I/O๊ฐ€ ์ค„์–ด๋“ค๋ฉด ๊ฐ™์ด ์ค„์–ด๋“ฆ

ORACLE OPTIMIZER

OPTIMIZER

OPTIMIZER

์˜ตํ‹ฐ๋งˆ์ด์ €๋Š” SQL ๋ฌธ์— ๋Œ€ํ•œ ์‹คํ–‰๊ณ„ํš์„ ์ƒ์„ฑํ•˜๋Š” ์˜ค๋ผํด ๋ฐ์ดํ„ฐ๋ฒ ์ด์Šค์˜ ์ผ๋ถ€์ด๋‹ค. ์‹คํ–‰๊ณ„ํš์˜ ๊ฒฐ์ •์€ SQL๋ฌธ ์ฒ˜๋ฆฌ์—์„œ ์ค‘์š”ํ•œ ๋‹จ๊ณ„์ด๋ฉฐ ์‹คํ–‰ ์‹œ๊ฐ„์— ํฐ ์˜ํ–ฅ์„ ์ค„ ์ˆ˜ ์žˆ๋‹ค. ์‹คํ–‰๊ณ„ํš์ด๋ž€ ๋ช…๋ น๋ฌธ์„ ์‹คํ–‰ํ•˜๊ธฐ ์œ„ํ•ด ์ˆœ์„œ๋Œ€๋กœ ์ˆ˜ํ–‰๋˜๋Š” ์ผ๋ จ์˜ ์ž‘์—…์„ ๋งํ•œ๋‹ค. ์˜ตํ‹ฐ๋งˆ์ด์ €๋Š” ์ฟผ๋ฆฌ์—์„œ ์ง€์ •๋œ ์กฐ๊ฑด๊ณผ ์ฐธ์กฐ๋˜๋Šฐ ๊ฐ์ฒด์™€ ๊ด€๋ จ๋œ ๋‹ค์Œ๊ณผ ๊ฐ™์€ ๋งŽ์€ ์š”์†Œ๋“ค์„ ๊ณ ๋ คํ•œ๋‹ค.

Cost based Optimizer

์˜ค๋ผํด์—์„œ ์ฐธ์กฐํ•˜๊ณ  ์žˆ๋Š” ์˜ตํ‹ฐ๋งˆ์ด์ €์ด๋‹ค. SQL ๋ฌธ์žฅ์ด ์ฐธ์กฐํ•˜๊ณ  ์žˆ๋Š” ๊ฐ์ฒด๋“ค์— ๋Œ€ํ•œ ์ˆ˜์ง‘๋œ ํ†ต๊ณ„ ์ •๋ณด์˜ ๊ฐ’๊ณผ ๋ฐ์ดํ„ฐ๋ฒ ์ด์Šค ํŒŒ๋ผ๋ฏธํ„ฐ ์„ค์ •๊ฐ’์„ ๊ธฐ์ดˆ๋กœ ๊ฐ€์žฅ ์ ์€ ๋น„์šฉ์ด ๋ฐœ์ƒํ•˜๋Š” ์‹คํ–‰๊ณ„ํš์„ ๊ฒฐ์ •ํ•˜๋Š” ์˜ตํ‹ฐ๋งˆ์ด์ €์ด๋‹ค. ์ฆ‰ ํ†ต๊ณ„ ์ •๋ณด๋ฅผ ํ™œ์šฉํ•ด SQL ์ˆ˜ํ–‰์‹œ ์†Œ์š”๋  ๋น„์šฉ์„ ์˜ˆ์ธกํ•˜๊ณ  ๊ทธ ๊ฐ’์„ ๊ธฐ์ค€์œผ๋กœ ์‹คํ–‰๊ณ„ํš์„ ๊ฒฐ์ •ํ•˜๋Š” ๊ฒƒ์ด๋‹ค.

Cost Based Optimizer Mode

  • ALL_ROWS: ์ผ๊ด„ ์ฒ˜๋ฆฌ ์ž‘์—… ๋“ฑ์— ๋Œ€ํ•œ ์ „์ฒด ์ฒ˜๋ฆฌ ์†๋„์— ๋Œ€ํ•ด ์ตœ์ ํ™”ํ•˜๋Š” ๋ฐฉ์‹์ด๋ฉฐ ๊ธฐ๋ณธ ๋ฐฉ์‹
  • FIRST_ROWS_N: OLTP ํ™˜๊ฒฝ์—์„œ ์ฒซ n๊ฐœ์˜ ๊ฒฐ๊ณผ๊ฐ€ ๋ฐ˜ํ™˜๋  ๋•Œ๊นŒ์ง€์˜ ์‹œ๊ฐ„์„ ๋‹จ์ถ•ํ•˜๊ธฐ ์œ„ํ•ด ์ตœ์ ํ™”ํ•˜๋Š” ๊ฒƒ์ด๋ฉฐ ๋น ๋ฅธ ์‘๋‹ต ์‹œ๊ฐ„์„ ์›ํ•  ๋•Œ ์‚ฌ์šฉ

Optimizer๊ฐ€ ํ•„์š”ํ•œ ์ด์œ 

์˜ตํ‹ฐ๋งˆ์ด์ €๋Š” ์‚ฌ์šฉ ๊ฐ€๋Šฅํ•œ ์•ก์„ธ์Šค ๊ฒฝ๋กœ๋ฅผ ๊ธฐ๋ฐ˜์œผ๋กœ SQL๋ฌธ์˜ ์ž ์žฌ์  ๊ณ„ํš ์ง‘ํ•ฉ์„ ์ƒ์„ฑํ•œ๋‹ค. ๋ฐ์ดํ„ฐ ๋ถ„ํฌ ๋ฐ ๋ช…๋ น๋ฌธ์—์„œ ์•ก์„ธ์Šคํ•œ ํ…Œ์ด๋ธ”๊ณผ ์ธ๋ฑ์Šค ์ €์žฅ ์˜์—ญ ํŠน์„ฑ์— ๋Œ€ํ•œ ํ†ต๊ณ„๋ฅผ ๊ธฐ๋ฐ˜์œผ๋กœ ๊ณ„ํš๋ณ„ ๋น„์šฉ์„ ์˜ˆ์ธกํ•œ๋‹ค. ์—ฌ๋Ÿฌ ๊ณ„ํš์˜ ๋น„์šฉ์„ ๋น„๊ตํ•˜๊ณ  ์ตœ์ € ๋น„์šฉ์˜ ๊ณ„ํš์„ ์„ ํƒํ•˜๊ธฐ ์œ„ํ•ด ์˜ตํ‹ฐ๋งˆ์ด์ €๋Š” ํ•„์š”ํ•˜๋‹ค.

Optimizer์˜ ๊ตฌ๋ฌธ ๋ถ„์„ ์ž‘์—… ์ค‘ ์ตœ์ ํ™”

  1. ๋ช…๋ น์–ด ๊ตฌ๋ถ„ ๋ถ„์„ (PARSE): ๋ฌธ๋ฒ•์  ์ฒดํฌ, ๋ฌธ๋งฅ์  ์ฒดํฌ, Shared Pool ์ฒดํฌ
  2. Optimizer
    1. ๋ช…๋ น์–ด ๋ณ€ํ˜•๊ธฐ (Query Transformer): SQL์„ ์ตœ์ ํ™”ํ•˜๊ธฐ ์‰ฌ์šด ํ˜•ํƒœ๋กœ ๋ณ€ํ™˜
    2. ์˜ˆ์ธก๊ธฐ (Estimator)
      1. Selectivity: ์ „์ฒด ๋Œ€์ƒ row ์ค‘์— ํŠน์ •ํ•œ ์กฐ๊ฑด์— ์˜ํ•ด ์„ ํƒ๋  ๊ฒƒ์œผ๋กœ ์˜ˆ์ƒ๋˜๋Š” row ๋น„์œจ
      2. Cardinality: ํŠน์ • ์•ก์„ธ์Šค ๋‹จ๊ณ„๋ฅผ ๊ฑฐ์น˜๊ณ  ๋‚˜์„œ ์ถœ๋ ฅ๋  ๊ฒƒ์œผ๋กœ ์˜ˆ์ƒ๋˜๋Š” ๊ฒฐ๊ณผ ๊ฑด์ˆ˜
      3. Cost: ํŠน์ • ๋ช…๋ น๋ฌธ์„ ์‹คํ–‰ํ•˜๋Š” ๋ฐ ํ•„์š”ํ•œ ํ‘œ์ค€ํ™”๋œ I/O์— ๋Œ€ํ•œ ์ตœ์  ์˜ˆ์ธก ๋น„์šฉ
    3. ๊ณ„ํš ์ƒ์„ฑ๊ธฐ (Plan Generator): ์ตœ์ ํ™”๋ฅผ ์œ„ํ•œ ์—ฌ๋Ÿฌ ๊ธฐ๋ฒ•์„ ์‹œ๋„ํ•˜๊ณ  ์˜ˆ์ธก๊ธฐ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๊ฐ ์ตœ์ ํ™” ์ œ์•ˆ์˜ ๋น„์šฉ ๊ณ„์‚ฐํ•œ ๋’ค ๋น„์šฉ์„ ๊ธฐ๋ฐ˜์œผ๋กœ ์ตœ์ƒ์˜ ์ตœ์ ํ™” ์ œ์•ˆ ์„ ํƒํ•œ ๋’ค ์‹คํ–‰ ๊ณ„ํš ์ƒ์„ฑ
  3. ์‹คํ–‰๊ณ„ํš์ƒ์„ฑ (Row Source Generator)

Optimizer์— ์˜ํ–ฅ์„ ๋ฏธ์น˜๋Š” ์š”์†Œ

  • ์ž‘์„ฑ๋œ ๋ช…๋ น์–ด
  • ํ…Œ์ด๋ธ”, ์ธ๋ฑ์Šค, ํŒŒํ‹ฐ์…˜ ๋“ฑ ์ œ๊ณต๋˜๋Š” ๋ฐ์ดํ„ฐ ๊ตฌ์กฐ
  • ํ†ต๊ณ„ ์ •๋ณด
  • ํžŒํŠธ
  • ์˜ตํ‹ฐ๋งˆ์ด์ € ๊ด€๋ จ ํŒŒ๋ผ๋ฏธํ„ฐ

Optimizer์˜ ํ•œ๊ณ„

  • ๋ถ€์กฑํ•œ Factor
  • ๋ถ€์ •ํ™•ํ•œ ํ†ต๊ณ„
  • Histogram์˜ ํ•œ๊ณ„
  • ์กฐ๊ฑด์ ˆ Column๋“ค์˜ ์ƒ๊ด€๊ด€๊ณ„
  • Bind ๋ณ€์ˆ˜ ์‚ฌ์šฉ์‹œ ๊ท ๋“ฑ๋ถ„ํฌ ๊ฐ€์ •
  • ๋™์ผ ๋น„์šฉ์˜ ๊ฒฝ์šฐ ์ตœ์‹ , ์•ŒํŒŒ๋ฒณ ์ˆ˜ ์ธ๋ฑ์Šค ์„ ํƒ ๊ทœ์น™
  • H/W ํŠน์ง• ๋ฐ˜์˜ํ•˜์ง€ ์•Š์Œ
  • ์กฐ์ธ ์ˆœ์„œ ๊ฒฐ์ •์‹œ ๊ฐ€๋Šฅํ•œ ๋ชจ๋“  ๊ฒฝ์šฐ๋ฅผ ๊ณ ๋ คํ•˜์ง€๋Š” ์•Š์Œ
  • ์ตœ์ ํ™”์— ์‚ฌ์šฉ๋˜๋Š” ์‹œ๊ฐ„ ์ œํ•œ

QUERY ๋ณ€ํ˜•๊ธฐ

QUERY ๋ณ€ํ˜•๊ธฐ

  • Heuristic Transformation ์˜ค๋ผํด์˜ ๊ฒฝํ—˜์น˜์— ์˜ํ•ด์„œ ํŠœ๋‹ํ•˜๋Š” ๋ฐฉ์‹์œผ๋กœ ๊ฑฐ์˜ ๋Œ€๋ถ€๋ถ„ ์ด ์‹คํ–‰ ๊ณ„ํš์„ ์„ ํƒ
  • Cost Based Transformation ์˜คํžˆ๋ ค ํŠœ๋‹๋œ ์‹คํ–‰๊ณ„ํš์ด ๋น„์šฉ์ด ๋” ๋‚˜๊ฐˆ ์ˆ˜ ์žˆ๊ธฐ ๋•Œ๋ฌธ์— ์˜ˆ์ธก์น˜๋กœ ๊ณ„์‚ฐํ•ด ๋ณด๊ณ  ๋น„์šฉ์ด ๋œ ๋“œ๋Š” ๋ฐฉ๋ฒ•์„ ์„ ํƒ

CSE(Common Subexpression Elimination)

WHERE ์ ˆ์—์„œ OR ์—ฐ์‚ฐ์‹œ ์‚ฌ์šฉ๋œ ์ค‘์ฒฉ๋œ ์กฐ๊ฑด์ ˆ์€ ์ œ๊ฑฐ

SELECT DEPARTMENT_ID, SALARY
FROM EMPLOYEE
WHERE (DEPARTMENT_ID = 10 AND SALARY = 4200)
**OR DEPARTMENT_ID = 10;**

JE(Join Elimination)

์ง์ ‘ ์‚ฌ์šฉํ•˜์ง€ ์•Š์€ ํ…Œ์ด๋ธ”์€ SQL์—์„œ ์‚ญ์ œ

SELECT E.EMPLOYEE_ID, E.LAST_NAME, E.SALARY
FROM EMPLOYEES E, DEPARTMENTS D
WHERE E.DEPARTMENT_ID = D.DEPARTMENT_ID
AND E.JOB_ID = 'SH_CLERK';

SELECT E.EMPLOYEE_ID, E.LAST_NAME, E.SALARY
FROM EMPLOYEES E, DEPARTMENTS D
AND E.JOB_ID = 'SH_CLERK';

์กฐ์ธ๊นŒ์ง€ ํ•  ํ•„์š”๊ฐ€ ์—†๋Š” ๋ช…๋ น์–ด์ผ ๊ฒฝ์šฐ (EMPLOYEE ํ…Œ์ด๋ธ”์˜ FK ๋ณด๊ณ  ํ™•์ธ) Single Table Access์˜ ์‹คํ–‰ ๊ณ„ํš ๋ณด์—ฌ ์คŒ

SJ(Semi Join)

์„œ๋ธŒ์ฟผ๋ฆฌ๋ฅผ semi join์œผ๋กœ ๋ณ€ํ™˜

SELECT D.DEPARTMENT_ID, D.DEPARTMENT_NAME, D.LOCATION_ID
FROM DEPARTMENTS D
WHERE EXIST (SELECT NULL FROM EMPLOYEE E
							WHERE E.DEPARTMENT_ID = D.DEPARTMENT_ID)
AND D.LOCATION_ID = 1700;

SELECT D.DEPARTMENT_ID, D.DEPARTMENT_NAME, D.LOCATION_ID
FROM DEPARTMENTS D, EMPLOYEE E
WHERE E.DEPARTMENT_ID = D.DEPARTMENT_ID)
AND D.LOCATION_ID = 1700;

์˜ˆ์ธก๊ธฐ

Selectivity

  • ์„ ํƒ์„ฑ = ์กฐ๊ฑด์„ ์ถฉ์กฑํ•˜๋Š” ํ–‰ ์ˆ˜ / ์ด ํ–‰ ์ˆ˜

์„ ํƒ์„ฑ์€ 0.0์—์„œ 1.0 ์‚ฌ์ด์˜ ๊ฐ’์œผ๋กœ ํ‘œํ˜„ํ•˜๋ฉฐ ํ†ต๊ณ„๊ฐ€ ์—†์„ ๊ฒฝ์šฐ ๋™์  ์ƒ˜ํ”Œ๋ง์„ ์‚ฌ์šฉํ•˜๋ฉฐ, ํžˆ์Šคํ† ๊ทธ๋žจ์ด ์—†์„ ๊ฒฝ์šฐ ํ–‰ ๋ถ„์‚ฐ์„ ๊ท ๋“ฑํ•œ ๊ฒƒ์œผ๋กœ ๊ฐ€์ •ํ•˜๊ณ  ๊ณ„์‚ฐํ•œ๋‹ค.

๊ธฐ๋ณธ๊ฐ’์˜ ๊ฐ€์ •์„ ์‚ฌ์šฉํ•  ๊ฒฝ์šฐ ์ตœ์  ์ˆ˜์ค€์— ๋ชป ๋ฏธ์น˜๋Š” ๊ณ„ํš์„ ์‚ฌ์šฉํ•˜๊ฒŒ ๋  ์ˆ˜๋„ ์žˆ๋‹ค. ๋”ฐ๋ผ์„œ ์˜ตํ‹ฐ๋งˆ์ด์ €์˜ ์˜ˆ์ธก์„ ๋”์šฑ ์ •ํ™•ํ•˜๊ฒŒ ํ•˜๊ธฐ ์œ„ํ•ด ํžˆ์Šคํ† ๊ทธ๋žจ ํ†ต๊ณ„๊ฐ’์„ ์ œ๊ณตํ•˜์—ฌ ์ •ํ™•๋„๋ฅผ ๋†’์ผ ์ˆ˜ ์žˆ๋‹ค.

-- ์ปฌ๋Ÿผ ํ†ต๊ณ„
SELECT NUM_DISTINCT, NUM_NULLS, NUM_BUCKETS, HISTOGRAM
FROM DBA_TABLE_COLUMNS
WHERE TABLE_NAME = 'EMPLOYEES'
AND COLUMN_NAME = 'JOB_ID'
AND OWNER = 'HR';

ํ†ต๊ณ„ ์ •๋ณด ์ œ๊ณต์€ Autotask์— ์˜ํ•ด ํ†ต๊ณ„๊ฐ€ ์ˆ˜์ง‘๋œ๋‹ค. ๋งค์ผ ํ•œ ๋ฒˆ์”ฉ ์˜ค๋ธŒ์ ํŠธ ํ†ต๊ณ„ ์ˆ˜์ง‘์ด ์ˆ˜ํ–‰๋œ๋‹ค. ํ†ต๊ณ„ ์ •๋ณด๊ฐ€ ์—†๊ฑฐ๋‚˜ ์ˆ˜์ง‘ ์ดํ›„ 10% ์ด์ƒ ๋ฐ์ดํ„ฐ๊ฐ€ ๋ณ€๋™๋œ ์˜ค๋ธŒ์ ํŠธ๋ฅผ ๋Œ€์ƒ์œผ๋กœ ์ง„ํ–‰๋œ๋‹ค. ํ˜น์€ ์•„๋ž˜ ๋ช…๋ น์–ด๋ฅผ ํ†ตํ•ด DBMS_STATS ํŒจํ‚ค์ง€๋ฅผ ํ†ตํ•ด ์ˆ˜๋™์œผ๋กœ ์‹คํ–‰ํ•  ์ˆ˜ ์žˆ๋‹ค.

begin
dbms_stats.gather_tables_stats('test', 'cp_emp'); -- test ์Šคํ‚ค๋งˆ์˜ cp_emp ํ…Œ์ด๋ธ” 
end;

ํ…Œ์ด๋ธ”์€ ์ƒ์„ฑ๋œ๋‹ค๊ณ  ํ†ต๊ณ„ ์ˆ˜์ง‘์ด ๋ฐ”๋กœ ๋˜์ง€ ์•Š์ง€๋งŒ, ์ธ๋ฑ์Šค๋Š” ์ƒ์„ฑ๋˜๋Š” ์ฆ‰์‹œ ํ†ต๊ณ„ ์ˆ˜์ง‘์ด ๋ฐ”๋กœ ์ด๋ฃจ์–ด์ง„๋‹ค.

Cardinality

  • ๊ธฐ์ˆ˜ = ์„ ํƒ๋„ * ์ด ํ–‰ ์ˆ˜

์‹คํ–‰๊ณ„ํš์˜ ๊ฐ ๋‹จ๊ณ„์˜ ๊ฒ€์ƒ‰ ํ–‰์˜ ์˜ˆ์ธก ์ˆ˜์ด๋‹ค. ์กฐ์ธ, ํ•„ํ„ฐ ๋ฐ ์ •๋ ฌ ๋น„์šฉ์„ ๊ฒฐ์ •ํ•  ์ค‘์š”ํ•œ ์ˆ˜์น˜์ด๋‹ค.

Cost

  • ๋น„์šฉ = (๋‹จ์ผ ๋ธ”๋ก IO ๋น„์šฉ + ๋ฉ€ํ‹ฐ ๋ธ”๋ก IO ๋น„์šฉ + CPU ๋น„์šฉ) / ๋‹จ์ผ ๋ธ”๋ก ์ฝ๊ธฐ ์‹œ๊ฐ„

์˜ตํ‹ฐ๋งˆ์ด์ €๊ฐ€ ์˜ˆ์ธกํ•œ ๋ช…๋ น์–ด๋ฅผ ์‹คํ–‰ํ•˜๋Š” ๋ฐ ํ•„์š”ํ•œ ํ‘œ์ค€ํ™”๋œ I/O ํšŸ์ˆ˜์ด๋‹ค. ๋น„์šฉ ๊ณต์‹์€ ์„ธ ๊ฐ€์ง€์˜ ๋‹ค๋ฅธ ๋น„์šฉ ๋‹จ์œ„๊ฐ€ ํฌํ•จ๋œ๋‹ค. ๋งŒ์•ฝ ๋น„์šฉ์ด 10์ด๋ผ๋ฉด 10๋ฒˆ์˜ Single Block I/O๋ฅผ ํ•œ ์‹œ๊ฐ„์ด๋ผ๊ณ  ์ƒ๊ฐํ•˜๋ฉด ๋œ๋‹ค.

์‹คํ–‰ ๊ณ„ํš ํ™•์ธ

EXPLAIN PLAN

EXPLAIN PLAN

์˜ตํ‹ฐ๋งˆ์ด์ €๊ฐ€ ์‹คํ–‰ ๊ณ„ํš์„ ์ƒ์„ฑํ•˜๊ณ  ์˜ˆ์ƒ ์‹คํ–‰ ๊ณ„ํš์„ PLAN_TABLE์— ์ €์žฅํ•œ๋‹ค. ๋ช…๋ น๋ฌธ์„ ์‹ค์ œ๋กœ ์‹คํ–‰ํ•˜์ง€๋Š” ์•Š๋Š”๋‹ค.

EXPLAIN PLAN FOR select * from employees where employee_id = 100;
SELECT * FROM TABLE(DBMS_XPLAN.DISPLAY);

PLAN_TABLE_OUTPUT
------------------------------------------------------------------------------------------------------------------------------------------------------
Plan hash value: 3541774394

----------------------------------------------------------------------------------------------
| Id  | Operation                   | Name           | Rows  | Bytes | Cost (%CPU)| Time     |
----------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT            |                |     1 |    67 |     1   (0)| 00:00:01 |
|   1 |  TABLE ACCESS BY INDEX ROWID| EMPLOYEES      |     1 |    67 |     1   (0)| 00:00:01 |
|*  2 |   INDEX UNIQUE SCAN         | EMPLOYEES_IX01 |     1 |       |     0   (0)| 00:00:01 |
----------------------------------------------------------------------------------------------
ํ•ญ๋ชฉ์„ค๋ช…
ID๊ฐ Operation ID
Operation์‹คํ–‰๋˜๋Š” job
NameOperation์ด ์•ก์„ธ์Šคํ•˜๋Š” ํ…Œ์ด๋ธ”, ์ธ๋ฑ์Šค
Rows๊ฐ Operation์ด ๋๋‚ฌ์„ ๋•Œ ๋ฆฌํ„ด๋˜๋Š” ๊ฑด์ˆ˜
Cost๊ฐ Operation์˜ Cost
Time์ˆ˜ํ–‰์‹œ๊ฐ„

PLAN_TABLE

์‹คํ–‰ ๊ณ„ํš์ด ์ €์žฅ๋˜๋Š” ํ…Œ์ด๋ธ”์ด๋ฉฐ ์˜ค๋ผํด์„ ์„ค์น˜ํ•˜๋ฉด ์ž๋™์œผ๋กœ ์ƒ์„ฑ๋œ๋‹ค. ์ด๋ฆ„๋งŒ ๋˜‘๊ฐ™๊ณ  ์„ธ์…˜๋งˆ๋‹ค ๋‹ค๋ฅธ ํ”Œ๋žœ ํ…Œ์ด๋ธ”์„ ์‚ฌ์šฉํ•œ๋‹ค. ์ฆ‰ ๊ณต์œ ๋˜๋Š” ํ…Œ์ด๋ธ”์ด ์•„๋‹ˆ๊ธฐ ๋•Œ๋ฌธ์— ์„ธ์…˜๋งˆ๋‹ค ๋…๋ฆฝ์ ์œผ๋กœ ์‚ฌ์šฉํ•œ๋‹ค.

SELECT OWNER, SYNONYM_NAME, TABLE_OWNER, TABLE_NAME
FROM ALL_SYNONYMS
WHERE SYNONYM_NAME = 'PLAN_TABLE';

OWNER                          SYNONYM_NAME                   TABLE_OWNER                    TABLE_NAME                    
------------------------------ ------------------------------ ------------------------------ ------------------------------
PUBLIC                         PLAN_TABLE                     SYS                            PLAN_TABLE$    

์‹คํ–‰ ๊ณ„ํš ์ฝ๊ธฐ

EXPLAIN PLAN FOR
SELECT *
FROM EMPLOYEES
WHERE EMPLOYEE_ID = 100;

SELECT * FROM TABLE(DBMS_XPLAN.DISPLAY);

Plan hash value: 3541774394
 
----------------------------------------------------------------------------------------------
| Id  | Operation                   | Name           | Rows  | Bytes | Cost (%CPU)| Time     |
----------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT            |                |     1 |    67 |     1   (0)| 00:00:01 |
|   1 |  TABLE ACCESS BY INDEX ROWID| EMPLOYEES      |     1 |    67 |     1   (0)| 00:00:01 |
|*  2 |   INDEX UNIQUE SCAN         | EMPLOYEES_IX01 |     1 |       |     0   (0)| 00:00:01 |
----------------------------------------------------------------------------------------------
 
Predicate Information (identified by operation id):
---------------------------------------------------
 
   2 - access("EMPLOYEE_ID"=100)
  1. ํ•˜์œ„ ๋‹จ๊ณ„๋Š” ๋“ค์—ฌ์“ฐ๊ธฐ ๋˜์–ด ์žˆ์Œ
  2. ํ•˜์œ„ ๋‹จ๊ณ„ ์ˆ˜ํ–‰ ํ›„ ์ƒ์œ„ ๋‹จ๊ณ„ ์ฒ˜๋ฆฌ
  3. ๋™์ผ LEVEL๋ผ๋ฆฌ๋Š” ๋จผ์ € ๋‚˜์˜จ ๋‹จ๊ณ„๋ถ€ํ„ฐ ์ˆ˜ํ–‰

์ด๋Ÿฐ ์‹คํ–‰ ๊ณ„ํš์ด ์žˆ๋‹ค๋ฉด, 4 โ†’ 3 โ†’ 6 โ†’ 5 โ†’ 2 โ†’ 8 โ†’ 7 โ†’ 1 โ†’ 0 ์ˆœ์„œ์ด๋‹ค.

AUTOTRACE

AUTOTRACE

SQL ๋ช…๋ น์˜ ์˜ˆ์ƒ ์‹คํ–‰ ๊ณ„ํš ๋ฐ ์‹คํ–‰ ํ†ต๊ณ„๋ฅผ ์ž๋™์œผ๋กœ ์–ป์„ ์ˆ˜ ์žˆ๋‹ค. AUTOTRACE ON์ด ๋˜์–ด ์žˆ์œผ๋ฉด ๋ชจ๋“  ๋ช…๋ น์–ด๊ฐ€ ๋ช…๋  ๊ฒฐ๊ณผ, ์‹คํ–‰ ํ”Œ๋žœ, ํ†ต๊ณ„ ์ •๋ณด๊ฐ€ ์„ธํŠธ๋กœ ๋ณด์—ฌ์ง„๋‹ค. ์ˆ˜ํ–‰ ํ†ต๊ณ„๋Š” V$ ํ…Œ์ด๋ธ”์— ์žˆ๋Š” ๋ฐ์ดํ„ฐ๋“ค์„ ์ฝ์–ด์™€์„œ ๋ณด์—ฌ ์ค€๋‹ค. ์ด๋Ÿด ๊ฒฝ์šฐ DBA์˜ ๊ถŒํ•œ์ด ํ•„์š”ํ•˜๊ธฐ ๋•Œ๋ฌธ์— ์ด๋ฅผ ์ฃผ์˜ํ•˜์ž. AUTOTRACE ๊ธฐ๋Šฅ์—๋Š” ์—ฌ๋Ÿฌ ๊ฐ€์ง€ ๋ช…๋ น ์˜ต์…˜๋“ค์ด ์žˆ๋‹ค.

  • OFF: AUTOTRACE ๋น„ํ™œ์„ฑํ™”
  • ON: AUTOTRACE ํ™œ์„ฑํ™”
  • TRACEONLY: AUTOTRACE ํ™œ์„ฑํ™”ํ•˜๊ณ  ๋ช…๋ น๋ฌธ์˜ ๊ฒฐ๊ณผ๋ฅผ ์ถœ๋ ฅํ•˜์ง€ ์•Š์Œ
  • EXPLAIN: ์‹คํ–‰ ๊ณ„ํš์€ ํ‘œ์‹œํ•˜์ง€๋งŒ ํ†ต๊ณ„๋ฅผ ํ‘œ์‹œํ•˜์ง€ ์•Š์Œ
  • STATISZTICS: ํ†ต๊ณ„๋Š” ํ‘œ์‹œํ•˜์ง€๋งŒ ์‹คํ–‰ ๊ณ„ํš์€ ํ‘œ์‹œํ•˜์ง€ ์•Š์Œ
SET AUTOTRACE ON
SELECT *
FROM EMPLOYEES
WHERE EMPLOYEE_ID = 100;

EMPLOYEE_ID FIRST_NAME                               LAST_NAME
----------- ---------------------------------------- --------------------------------------------------
EMAIL                                              PHONE_NUMBER                             HIRE_DATE  JOB_ID          SALARY COMMISSION_PCT
-------------------------------------------------- ---------------------------------------- ---------- -------------------- ---------- --------------
MANAGER_ID DEPARTMENT_ID
---------- -------------
        100 Steven                                   King
SKING                                              515.123.4567                             2003/06/17 AD_PRES          24000
                      90

1 row selected.

Elapsed: 00:00:00.01

Execution Plan
----------------------------------------------------------
Plan hash value: 3541774394

----------------------------------------------------------------------------------------------
| Id  | Operation                   | Name           | Rows  | Bytes | Cost (%CPU)| Time     |
----------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT            |                |     1 |    67 |     1   (0)| 00:00:01 |
|   1 |  TABLE ACCESS BY INDEX ROWID| EMPLOYEES      |     1 |    67 |     1   (0)| 00:00:01 |
|*  2 |   INDEX UNIQUE SCAN         | EMPLOYEES_IX01 |     1 |       |     0   (0)| 00:00:01 |
----------------------------------------------------------------------------------------------

Predicate Information (identified by operation id):
---------------------------------------------------

   2 - access("EMPLOYEE_ID"=100)

Statistics
----------------------------------------------------------
          1  recursive calls
          0  db block gets
          2  consistent gets
          0  physical reads
          0  redo size
       1167  bytes sent via SQL*Net to client
        512  bytes received via SQL*Net from client
          1  SQL*Net roundtrips to/from client
          0  sorts (memory)
          0  sorts (disk)
          1  rows processed

ํ†ต๊ณ„์— ๋Œ€ํ•œ ํ•ญ๋ชฉ ์„ค๋ช…์€ ๋‹ค์Œ๊ณผ ๊ฐ™๋‹ค.

ํ•ญ๋ชฉ์„ค๋ช…
recursive calls์œ ์ € ๋ ˆ๋ฒจ๊ณผ ์‹œ์Šคํ…œ ๋ ˆ๋ฒจ์—์„œ ์ƒ์„ฑ๋˜๋Š” recursive call ์ˆ˜
db block getsCurrent ๋ชจ๋“œ๋กœ ์ฝ์€ ๋ธ”๋ก ์ˆ˜
consistent getsConsistents ๋ชจ๋“œ๋กœ ์ฝ์€ ๋ธ”๋ก ์ˆ˜
physical reads๋””์Šคํฌ์—์„œ ์ฝ์€ ๋ธ”๋ก ์ˆ˜
redo size์ด ๋ฆฌ๋‘ ์–‘
bytes sent via SQL*Net to client์„œ๋ฒ„ ํ”„๋กœ์„ธ์Šค์—์„œ ํด๋ผ์ด์–ธํŠธ๋กœ ๋ณด๋‚ธ ์ด ๋ฐ”์ดํŠธ ์ˆ˜
bytes received via SQL*Net from client์˜ค๋ผํด๋„ท์„ ํ†ตํ•ด ํด๋ผ์ด์–ธํŠธ์—์„œ ๋ฐ›์€ ์ด ๋ฐ”์ดํŠธ ์ˆ˜
SQL*Net roundtrips to/from clientํด๋ผ์ด์–ธํŠธ๊ฐ€ ๋ฐœํ–‰ํ•œ fetch all ํšŸ์ˆ˜
sorts (memory)๋ฉ”๋ชจ๋ฆฌ์—์„œ ์™„์ „ํžˆ ์ˆ˜ํ–‰๋˜์–ด ๋””์Šคํฌ ์“ฐ๊ธฐ๊ฐ€ ํ•„์š”ํ•˜์ง€ ์•Š์€ ์ •๋ ฌ ์ž‘์—…์˜ ์ˆ˜
sorts (disk)์ตœ์†Œํ•œ ํ•˜๋‚˜์˜ ๋””์Šคํฌ ์“ฐ๊ธฐ๊ฐ€ ํ•„์š”ํ•œ ์ •๋ ฌ ์ž‘์—… ์ˆ˜
rows processed์กฐํšŒ ๊ฑด์ˆ˜

V$SQL_PLAN

V$SQL_PLAN

V$SQL_PLAN์€ ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ ์บ์‹œ์— ์žˆ๋Š” SQL ์ปค์„œ์˜ ์‹ค์ œ๋กœ ์‚ฌ์šฉ๋œ ์‹คํ–‰ ๊ณ„ํš์„ ์ œ๊ณตํ•œ๋‹ค. ๋”ฐ๋ผ์„œ DBMS_XPLAN.DISPLAY_CURSOR(โ€™sql_idโ€™, child_number, โ€˜formatโ€™)์„ ์ด์šฉํ•ด ์‹คํ–‰ ๊ณ„ํš์„ ์ถœ๋ ฅํ•œ๋‹ค.

v$sql ํ…Œ์ด๋ธ”์— ์‹คํ–‰ํ•œ SQL์ด ๋ชจ๋‘ ์ €์žฅ๋˜์–ด ์žˆ๋‹ค. ๋”ฐ๋ผ์„œ ์—ฌ๊ธฐ์—์„œ ๋‚ด๊ฐ€ ์กฐ์‚ฌํ•˜๊ณ  ์‹ถ์€ SQL์„ ๊ฒ€์ƒ‰ํ•œ ๋’ค์— sql_id๋ฅผ ์•Œ์•„๋‚ด์•ผ ํ•œ๋‹ค.

ํ˜„์žฌ ์„ธ์…˜์—์„œ ์ง์ „์— ์ˆ˜ํ–‰ํ•œ SQL์˜ ๊ฒฝ์šฐ๋Š” sql_id, child_number๋ฅผ NULL๋กœ ์ง€์ •ํ•˜๊ฑฐ๋‚˜ ์ƒ๋žต ๊ฐ€๋Šฅํ•˜๋‹ค.

-- SQL ID ์ฐพ๊ธฐ
SELECT SQL_ID, SQL_TEXT
FROM v$sql
WHERE SQL_TEXT LIKE '%SELECT E.LAST_NAME, %';

-- ์‹คํ–‰ ๊ณ„ํš ๋ณด์—ฌ ์ฃผ๊ธฐ
SELECT * 
FROM TABLE(DBMS_XPLAN.DISPLAY_CURSOR('43tystsdw8hmp'));

์‹คํ–‰ ๊ณ„ํš์€ ์‹ค์ œ ์‚ฌ์šฉํ•œ ๊ฒƒ์ด ๋งž์ง€๋งŒ ํ•จ๊ป˜ ๋ณด์—ฌ ์ฃผ๋Š” ํ†ต๊ณ„๊ฐ’์€ ์˜ตํ‹ฐ๋งˆ์ด์ €์˜ ์˜ˆ์ธก์น˜๋‹ค.

V$SQL_PLAN_STATISTICS_ALL

V$SQL_PLAN_STATISTICS_ALL์€ ๋‹จ๊ณ„๋ณ„ ์‹คํ—˜ ํ†ต๊ณ„๋ฅผ ์ œ๊ณตํ•œ๋‹ค. STATISTIC_LEVEL์„ ALL๋กœ ์„ค์ •ํ•˜๊ณ  SQL์„ ์‹คํ–‰ํ•œ ๋’ค์— ์‹ค์ œ ์‚ฌ์šฉํ•œ ์‹คํ–‰ ํ†ต๊ณ„๋ฅผ ์•Œ ์ˆ˜ ์žˆ๋‹ค. ๋”ฐ๋ผ์„œ ์ด๋ฅผ ํ†ตํ•ด ์˜ตํ‹ฐ๋งˆ์ด์ €์˜ ์˜ˆ์ธก์น˜์™€ ์‹ค์ œ ํ†ต๊ณ„๊ฐ€ ์ผ์น˜ํ•œ์ง€ ํ™•์ธ ๋ฐ ๊ฒ€์ฆํ•  ์ˆ˜ ์žˆ๋‹ค.

ALTER SESSION SET STATISTICS_LEVEL=ALL;

SELECT E.LAST_NAME, D.DEPARTMENT_NAME
FROM HR.EMPLOYEES E, HR.DEPARTMENTS D
WHERE E.DEPARTMENT_ID = D.DEPARTMENT_ID;

ALTER SESSION SET STATISTICS_LEVEL=TYPICAL;

SELECT * FROM TABLE(DBMS_XPLAN.DISPLAY_CURSOR(null, null, 'ALLSTATS LAST'));

SQL_ID  5bd1y8jpdkm7g, child number 0
-------------------------------------
SELECT E.LAST_NAME, D.DEPARTMENT_NAME FROM HR.EMPLOYEES E, 
HR.DEPARTMENTS D WHERE E.DEPARTMENT_ID = D.DEPARTMENT_ID
 
Plan hash value: 1473400139
 
------------------------------------------------------------------------------------------------------------------------------------------------
| Id  | Operation                    | Name              | Starts | E-Rows | A-Rows |   A-Time   | Buffers | Reads  |  OMem |  1Mem | Used-Mem |
------------------------------------------------------------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT             |                   |      1 |        |     50 |00:00:00.01 |       8 |      6 |       |       |          |
|   1 |  MERGE JOIN                  |                   |      1 |    106 |     50 |00:00:00.01 |       8 |      6 |       |       |          |
|   2 |   TABLE ACCESS BY INDEX ROWID| DEPARTMENTS       |      1 |     27 |      5 |00:00:00.01 |       2 |      2 |       |       |          |
|   3 |    INDEX FULL SCAN           | DEPT_ID_PK        |      1 |     27 |      5 |00:00:00.01 |       1 |      1 |       |       |          |
|*  4 |   SORT JOIN                  |                   |      5 |    107 |     50 |00:00:00.01 |       6 |      4 | 73728 | 73728 |          |
|   5 |    VIEW                      | index$_join$_001  |      1 |    107 |    106 |00:00:00.01 |       6 |      4 |       |       |          |
|*  6 |     HASH JOIN                |                   |      1 |        |    106 |00:00:00.01 |       6 |      4 |  1096K|  1096K| 1541K (0)|
|   7 |      INDEX FAST FULL SCAN    | EMP_DEPARTMENT_IX |      1 |    107 |    106 |00:00:00.01 |       3 |      2 |       |       |          |
|   8 |      INDEX FAST FULL SCAN    | EMP_NAME_IX       |      1 |    107 |    107 |00:00:00.01 |       3 |      2 |       |       |          |
------------------------------------------------------------------------------------------------------------------------------------------------
ํ•ญ๋ชฉ์„ค๋ช…
Id๊ฐ ๋‹จ๊ณ„ ID
Operation์‹คํ–‰๋˜๋Š” Job
Name๋‹จ๊ณ„์—์„œ ์•ก์„ธ์Šคํ•˜๋Š” ํ…Œ์ด๋ธ”, ์ธ๋ฑ์Šค
Starts๊ฐ ๋‹จ๊ณ„๋ฅผ ๋ฐ˜๋ณต ์‹คํ–‰ํ•œ ํšŸ์ˆ˜
E-Rows๊ฐ ๋‹จ๊ณ„์—์„œ ๋ฆฌํ„ดํ•˜๋Š” ๊ฑด์ˆ˜ (์˜ˆ์ƒ)
A-Rows๊ฐ ๋‹จ๊ณ„์—์„œ ๋ฆฌํ„ดํ•˜๋Š” ๊ฑด์ˆ˜ (์‹ค์ œ)
A-Time๊ฐ ๋‹จ๊ณ„๋ณ„ ์†Œ์š” ์‹œ๊ฐ„ (๋ˆ„์ )
Buffers๊ฐ ๋‹จ๊ณ„๋ณ„ ์ฝ์€ ์ด ๋ธ”๋ก (๋ˆ„์ )
Reads๊ฐ ๋‹จ๊ณ„๋ณ„ ๋””์Šคํฌ์—์„œ ์ฝ์€ ๋ธ”๋ก ์ˆ˜
OMemOpotimal์ผ ๋•Œ ์˜ˆ์ƒ๋˜๋Š” PGA (๋ชจ๋‘ ๋ฉ”๋ชจ๋ฆฌ์—์„œ ์ฒ˜๋ฆฌ)
1MemOne-PASS์ผ ๋•Œ ์˜ˆ์ƒ๋˜๋Š” PGA (๋””์Šคํฌ ํ•œ ๋ฒˆ ์ฝ์–ด์˜ด)
Used-Mem์‹ค์ œ ์‚ฌ์šฉ๋œ PGA

SQL Trace

SQL Trace

์ผ๋ฐ˜์ ์œผ๋กœ ์„ธ์…˜ ๋ ˆ๋ฒจ์—์„œ ํ™œ์„ฑํ™”๋œ๋‹ค. ์„ธ์…˜๋ณ„๋กœ ๊ทธ๋ฃนํ™”๋œ SQL ๋ฌธ์— ๋Œ€ํ•œ ํ†ต๊ณ„๋ฅผ ์ˆ˜์ง‘ํ•˜๊ณ , tkprof ์œ ํ‹ธ๋ฆฌํ‹ฐ๋ฅผ ์ด์šฉํ•ด ์ฝ๊ธฐ ์‰ฌ์šด ์ถœ๋ ฅ์„ ์ƒ์„ฑํ•œ๋‹ค. ๋งˆ์น˜ ํ†ต๊ณ„์— ๋Œ€ํ•œ ๋กœ๊ทธ ํŒŒ์ผ์„ OS์— ์ €์žฅํ•œ๋‹ค๊ณ  ์ƒ๊ฐํ•˜๋ฉด ๋œ๋‹ค. OS๊ฐ€ FTP๊ฐ€ ๊ฐ€๋Šฅํ•œ ๊ณ„์ •์ด์–ด์•ผ ํ•œ๋‹ค๋Š” ์ œ์•ฝ ์กฐ๊ฑด์ด ์žˆ๋‹ค.

  1. ์ดˆ๊ธฐํ™” ํŒŒ๋ผ๋ฏธํ„ฐ ์„ค์ •
  2. TRACE ํ™œ์„ฑํ™”
  3. ์‘์šฉ ํ”„๋กœ๊ทธ๋žจ ์‹คํ–‰
  4. TRACE ๋น„ํ™œ์„ฑํ™”
  5. TKPROF๋กœ TRACE FILE ๋ณ€ํ™˜
  6. ์ถœ๋ ฅ ๊ฒฐ๊ณผ ํ•ด์„
SELECT name, value FROM v$diag_info;
ALTER SESSION SET tracefile_identifier='case1';
exec DBMS_SESSION.SESSION_TRACE_ENABLE(waits=>true);
SELECT * FROM HR.EMPLOYEES WHERE EMPLOYEE_ID = 102;
exec DBMS_SESSION.SESSION_TRACE_DISABLE;
tkprof xe_ora_19216_case1.trc report_1.txt sys=no
type report_1.txt

TKPROF: Release 11.2.0.2.0 - Development on ์›” 8์›” 18 16:54:27 2025

Copyright (c) 1982, 2009, Oracle and/or its affiliates.  All rights reserved.

Trace file: xe_ora_19216_case1.trc
Sort options: default

********************************************************************************
count    = number of times OCI procedure was executed
cpu      = cpu time in seconds executing
elapsed  = elapsed time in seconds executing
disk     = number of physical reads of buffers from disk
query    = number of buffers gotten for consistent read
current  = number of buffers gotten in current mode (usually for update)
rows     = number of rows processed by the fetch or execute call
********************************************************************************

SQL ID: 06m0pgb53b824 Plan Hash: 0

BEGIN DBMS_SESSION.SESSION_TRACE_ENABLE(waits=>true); END;

call     count       cpu    elapsed       disk      query    current        rows
------- ------  -------- ---------- ---------- ---------- ----------  ----------
Parse        0      0.00       0.00          0          0          0           0
Execute      1      0.00       0.00          1        100          0           1
Fetch        0      0.00       0.00          0          0          0           0
------- ------  -------- ---------- ---------- ---------- ----------  ----------
total        1      0.00       0.00          1        100          0           1

Misses in library cache during parse: 0
Misses in library cache during execute: 1
Optimizer mode: ALL_ROWS
Parsing user id: 48

Elapsed times include waiting on following events:
  Event waited on                             Times   Max. Wait  Total Waited
  ----------------------------------------   Waited  ----------  ------------
  SQL*Net message to client                       1        0.00          0.00
  SQL*Net message from client                     1       24.21         24.21
********************************************************************************

SQL ID: gmp19j6mx7njy Plan Hash: 1833546154

SELECT *
FROM
 HR.EMPLOYEES WHERE EMPLOYEE_ID = 102

call     count       cpu    elapsed       disk      query    current        rows
------- ------  -------- ---------- ---------- ---------- ----------  ----------
Parse        1      0.00       0.00          0          0          0           0
Execute      1      0.00       0.00          0          0          0           0
Fetch        2      0.00       0.00          0          2          0           1
------- ------  -------- ---------- ---------- ---------- ----------  ----------
total        4      0.00       0.00          0          2          0           1

Misses in library cache during parse: 1
Optimizer mode: ALL_ROWS
Parsing user id: 48
Number of plan statistics captured: 1

Rows (1st) Rows (avg) Rows (max)  Row Source Operation
---------- ---------- ----------  ---------------------------------------------------
         1          1          1  TABLE ACCESS BY INDEX ROWID EMPLOYEES (cr=2 pr=0 pw=0 time=6 us cost=1 size=69 card=1)
         1          1          1   INDEX UNIQUE SCAN EMP_EMP_ID_PK (cr=1 pr=0 pw=0 time=2 us cost=0 size=0 card=1)(object id 16413)

Elapsed times include waiting on following events:
  Event waited on                             Times   Max. Wait  Total Waited
  ----------------------------------------   Waited  ----------  ------------
  SQL*Net message to client                       2        0.00          0.00
  SQL*Net message from client                     2       23.20         23.20
********************************************************************************

SQL ID: 9wuhwhad81d36 Plan Hash: 0

BEGIN DBMS_SESSION.SESSION_TRACE_DISABLE; END;

call     count       cpu    elapsed       disk      query    current        rows
------- ------  -------- ---------- ---------- ---------- ----------  ----------
Parse        1      0.00       0.00          0          0          0           0
Execute      1      0.00       0.00          0          0          0           1
Fetch        0      0.00       0.00          0          0          0           0
------- ------  -------- ---------- ---------- ---------- ----------  ----------
total        2      0.00       0.00          0          0          0           1

Misses in library cache during parse: 1
Optimizer mode: ALL_ROWS
Parsing user id: 48

********************************************************************************

OVERALL TOTALS FOR ALL NON-RECURSIVE STATEMENTS

call     count       cpu    elapsed       disk      query    current        rows
------- ------  -------- ---------- ---------- ---------- ----------  ----------
Parse        2      0.00       0.00          0          0          0           0
Execute      3      0.00       0.00          1        100          0           2
Fetch        2      0.00       0.00          0          2          0           1
------- ------  -------- ---------- ---------- ---------- ----------  ----------
total        7      0.00       0.01          1        102          0           3

Misses in library cache during parse: 2
Misses in library cache during execute: 1

Elapsed times include waiting on following events:
  Event waited on                             Times   Max. Wait  Total Waited
  ----------------------------------------   Waited  ----------  ------------
  SQL*Net message to client                       3        0.00          0.00
  SQL*Net message from client                     3       24.21         47.42

OVERALL TOTALS FOR ALL RECURSIVE STATEMENTS

call     count       cpu    elapsed       disk      query    current        rows
------- ------  -------- ---------- ---------- ---------- ----------  ----------
Parse       12      0.00       0.00          0          0          0           0
Execute    199      0.01       0.01          0          0          0           0
Fetch      246      0.00       0.00          0        652          0        1735
------- ------  -------- ---------- ---------- ---------- ----------  ----------
total      457      0.01       0.01          0        652          0        1735

Misses in library cache during parse: 10
Misses in library cache during execute: 10

    3  user  SQL statements in session.
   12  internal SQL statements in session.
   15  SQL statements in session.
********************************************************************************
Trace file: xe_ora_19216_case1.trc
Trace file compatibility: 11.1.0.7
Sort options: default

       1  session in tracefile.
       3  user  SQL statements in trace file.
      12  internal SQL statements in trace file.
      15  SQL statements in trace file.
      15  unique SQL statements in trace file.
     792  lines in trace file.
      47  elapsed seconds in trace file.
ํ•ญ๋ชฉ์„ค๋ช…
call๋ช…๋ น์–ด ์ฒ˜๋ฆฌ ๋‹จ๊ณ„์— ๋”ฐ๋ฅธ ํ†ต๊ณ„ ์ •๋ณด
count๊ฐ ๋‹จ๊ณ„๊ฐ€ ์ˆ˜ํ–‰๋œ ํšŸ์ˆ˜
cpu์ฒ˜๋ฆฌ์— ์†Œ์š”๋˜๋Š” ์‹œ๊ฐ„
elapsed์‹คํ–‰์— ์†Œ์š”๋˜๋Š” ์ด ๊ฒฝ๊ณผ ์‹œ๊ฐ„
disk๋ฌผ๋ฆฌ์  ๋ธ”๋ก ์ฝ๊ธฐ ์ˆ˜
query์ผ๊ด€์„ฑ ์žˆ๋Š” ๋ชจ๋“œ์—์„œ ๋…ผ๋ฆฌ์  ๋ฒ„ํผ ์ฝ๊ธฐ ์ˆ˜
currentํ˜„์žฌ ๋ชจ๋“œ์—์„œ ๋…ผ๋ฆฌ์  ๋ฒ„ํผ ์ฝ๊ธฐ ์ˆ˜
rowsfetch, execute์— ์˜ํ•ด ์ฒ˜๋ฆฌ๋œ ํ–‰ ์ˆ˜

์ธ๋ฑ์Šค ์‚ฌ์šฉ ํŠœ๋‹

TABLE ACCESS

Full Table Scan

๋‹ค์ค‘ ๋ธ”๋ก ์ฝ๊ธฐ ์ˆ˜ํ–‰์œผ๋กœ High-Water Mark ์•„๋ž˜์˜ ๋ชจ๋“  ๋ธ”๋ก์„ ์ฝ๋Š”๋‹ค. ํ–‰ ํ•„ํ„ฐ๋ง์ด ๊ฐ€๋Šฅํ•˜๊ณ  ๋งŽ์€ ์–‘์˜ ๋ฐ์ดํ„ฐ๋ฅผ ์ฒ˜๋ฆฌํ•˜๋Š” ๊ฒฝ์šฐ Index Scan๋ณด๋‹ค ๋น ๋ฅด๋‹ค. ์‚ฌ์šฉ ์‚ฌ๋ก€๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™๋‹ค.

  • ์ ์ ˆํ•œ ์ธ๋ฑ์Šค๊ฐ€ ์—†์Œ
  • ๋‚ฎ์€ ์„ ํƒ์  ํ•„ํ„ฐ (ํ•„ํ„ฐ๊ฐ€ ๊ฑฐ์˜ ์—†์Œ)
  • ์ž‘์€ ํ…Œ์ด๋ธ”
  • ๋†’์€ ๋ณ‘๋ ฌ๋„
  • ์ „์ฒด ํ…Œ์ด๋ธ” ์Šค์บ” ํžŒํŠธ: FULL

Rowid Scan

ROWID๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ํ•˜๋‚˜์˜ ํ–‰๋งŒ ๋ฐ”๋กœ ์ฝ์–ด์˜ค๋Š” ๋ฐฉ์‹์ด๋‹ค. ์‚ฌ์šฉ๋˜๋Š” ๊ฒฝ์šฐ๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™๋‹ค.

  • User Rowid, Index Rowid๋ฅผ ์ด์šฉํ•˜์—ฌ ์†Œ๋Ÿ‰์˜ ๋ฐ์ดํ„ฐ ๊ฒ€์ƒ‰์ด ์œ ์šฉํ•  ๋•Œ
  • Single Block I/O ์ˆ˜ํ–‰
  • ROWID: Obeject ID (4bytes) + Datafile Number (1.5bytes) + Block Number (2.5bytes) + Row Number (2bytes)

B Tree Index๊ฐ€ ํ•„์š”ํ•œ ์ด์œ 

RowID๋ฅผ ์ด์šฉํ•ด์„œ ๊ฐ’์„ ์ฐพ์œผ๋Ÿฌ ๊ฐˆ ๋•Œ, ๋ชจ๋“  Row์˜ RowID๋ฅผ ์™ธ์šฐ๊ณ  ์žˆ์„ ์ˆ˜๋Š” ์—†๋‹ค. ๊ทธ๋ ‡๋‹ค๋ฉด ์ฐพ๊ณ ์ž ํ•˜๋Š” ๋ฐ์ดํ„ฐ์— ๋Œ€ํ•œ RowID๋ฅผ ์•Œ์•„์•ผ ํ•˜๋Š”๋ฐ, ์ด RowID๋ฅผ ์•Œ๊ธฐ ์œ„ํ•ด ์ธ๋ฑ์Šค ํ…Œ์ด๋ธ”์„ ์•ž์—์„œ๋ถ€ํ„ฐ ์ญ‰ ํ›‘๋Š” ๊ฒƒ ์—ญ์‹œ ๋น„ํšจ์œจ์ ์ด๋‹ค. ๋”ฐ๋ผ์„œ B+Tree Index๋ฅผ ์‚ฌ์šฉํ•ด ์ด์ง„ ํƒ์ƒ‰์„ ํ†ตํ•ด ์ธ๋ฑ์Šค๋ฅผ ์ฐพ๋Š” ์†๋„๋ฅผ ๋†’์ธ๋‹ค.

๋ฃจํŠธ ๋…ธ๋“œ์—๋Š” LMC(Left Most Child) ๊ฐ’์„ ๊ธฐ๋กํ•˜์—ฌ ๋ฆฌํ”„ ๋ธ”๋ก์„ ์ฐพ์•„๊ฐ€๋Š” ๊ตฌ์กฐ์ด๋‹ค.

B Tree Index ๊ตฌ์กฐ

  • ์ธ๋ฑ์Šค: ์ธ๋ฑ์Šค ํ•ญ๋ชฉ ํ—ค๋” + ํ‚ค ์—ด ๊ธธ์ด + ํ‚ค ์—ด ๊ฐ’ + ROWID

๊ฐ B+ Tree ์ธ๋ฑ์Šค์˜ ๊ฒ€์ƒ‰ ์‹œ์ž‘์ ์€ ๋ฃจํŠธ ๋ธ”๋ก์ด๋‹ค. ํ•ญ๋ชฉ ์ˆ˜์— ๋”ฐ๋ผ ์—ฌ๋Ÿฌ ๊ฐœ์˜ ๋ถ„๊ธฐ ๋ธ”๋ก์œผ๋กœ ๊ฐˆ๋ผ์ง€๊ณ  ์—ฌ๊ธฐ์„œ ๋‹ค์‹œ ์—ฌ๋Ÿฌ ๊ฐœ์˜ ์ตœํ•˜์œ„ ๋ธ”๋ก๋“ค์ด ์žˆ๋‹ค. ์ธ๋ฑ์Šค๋Š” ํ•ญ์ƒ ๊ท ํ˜•์„ ์ด๋ฃจ๋ฉฐ ์œ„์—์„œ ์•„๋ž˜๋กœ ํ™•์žฅํ•œ๋‹ค. ๊ท ํ˜• ์•Œ๊ณ ๋ฆฌ์ฆ˜์— ์˜ํ•ด B+Tree ๋†’์ด๊ฐ€ ๋ถˆํ•„์š”ํ•˜๊ฒŒ ์ปค์งˆ ์ˆ˜๋„ ์žˆ๋Š”๋ฐ, ๊ทธ๋Ÿฐ ๊ฒฝ์šฐ ์ธ๋ฑ์Šค๋ฅผ ์žฌ๊ตฌ์„ฑํ•œ๋‹ค.

B+ Tree ์ธ๋ฑ์Šค์˜ ๋‚ด๋ถ€ ๊ตฌ์กฐ๋Š” ์ธ๋ฑ์Šคํ™”๋œ ์ปฌ๋Ÿผ๊ฐ’์— ๋Œ€ํ•œ ์‹ ์†ํ•œ ์•ก์„ธ์Šค๋ฅผ ํ—ˆ์šฉํ•œ๋‹ค.

  • ์ปฌ๋Ÿผ์˜ ๊ฐ’, ROWID๊ฐ€ ํ•ญ์ƒ ์ •๋ ฌ๋œ ๊ฐ’ ์œ ์ง€
  • ์ปฌ๋Ÿผ์˜ ๊ฐ’์€ null์„ ์ œ์™ธํ•œ ๋ชจ๋“  ๊ฐ’ ๋ณด์œ 
  • Root, Branch, Leaf Block์„ ์ด์šฉํ•˜์—ฌ Tree ๊ตฌ์กฐ๋กœ ์˜ค๋ผํด์ด ์ž๋™ ๊ด€๋ฆฌ
  • ์ƒ์„ฑ
    • PK, Unique ์ œ์•ฝ ์กฐ๊ฑด์ด ์„ ์–ธ๋œ ์ปฌ๋Ÿผ์œผ๋กœ ์ž๋™ ์ƒ์„ฑ
    • ์œ ์ €๊ฐ€ ์„ฑ๋Šฅ ํ–ฅ์ƒ์„ ์œ„ํ•ด ์ˆ˜๋™ ์ƒ์„ฑ

Index Range Scan

์ธ๋ฑ์Šค์˜ root, branch, leaf block๊นŒ์ง€ ์ˆ˜์ง์ ์œผ๋กœ ํƒ์ƒ‰ํ•œ ํ›„์— leaf block์—์„œ ํ•„์š”ํ•œ ๋ฒ”์œ„๋งŒ ์ˆ˜ํ‰์ ์œผ๋กœ ํƒ์ƒ‰ํ•˜๋Š” ๋ฐฉ์‹์ด๋‹ค. ๋”ฐ๋ผ์„œ root, branch๋Š” ์ฒซ ๋ฒˆ์งธ์˜ leaf block์„ ํƒ์ƒ‰ํ•  ๋•Œ๋งŒ ํ•œ ๋ฒˆ์”ฉ ๊ฑฐ์น˜๊ณ , ์ดํ›„์—๋Š” leaf block์„ ์ˆ˜ํ‰์ ์œผ๋กœ ์ญ‰ ํ›‘๋Š”๋‹ค.

Single Block Read๋ฅผ ์ˆ˜ํ–‰ํ•˜๋ฉฐ, ์šฐ๋ฆฌ๊ฐ€ ์ธ๋ฑ์Šค๋ฅผ ์„ค์ •ํ•˜๋Š” ๊ฐ€์žฅ ๊ธฐ๋ณธ์ ์ธ ์ด์œ ๋Š” ์ด Index Range Scan์„ ์ง„ํ–‰ํ•˜๊ธฐ ์œ„ํ•ด์„œ์ด๋‹ค. ๊ธฐ๋ณธ์ ์œผ๋กœ ASC์œผ๋กœ ์ ‘๊ทผํ•œ๋‹ค. ์ˆœ์„œ๋ฅผ ์ •๋ฆฌํ•œ๋‹ค๋ฉด ๋‹ค์Œ๊ณผ ๊ฐ™๋‹ค.

  1. ์ˆ˜์ง ์Šค์บ”: ์กฐ๊ฑด์— ๋งž๋Š” ์ฒซ ํ‚ค ๊ฐ’์„ ์ฐพ๊ธฐ (Root โ†’ Branch โ†’ Leaf)
  2. ์ˆ˜ํ‰ ์Šค์บ”: ์กฐ๊ฑด์— ๋งž๋Š” ํ‚ค ๊ฐ’์ด ๋” ์ด์ƒ ๋‚˜์˜ค์ง€ ์•Š์„ ๋•Œ๊นŒ์ง€ Leaf ๋ธ”๋ก์„ ์Šค์บ”ํ•˜๋Š” ROWID๋ฅผ ์•Œ์•„๋ƒ„
  3. ํ…Œ์ด๋ธ” ์•ก์„ธ์Šค: ์ธ๋ฑ์Šค ์Šค์บ”์œผ๋กœ ์•Œ์•„๋‚ธ ROWID๋ฅผ ํ†ตํ•ด ํ…Œ์ด๋ธ”์„ ์ฐพ์•„๊ฐ (Random I/O)

์ธ๋ฑ์Šค๋Š” ์—ฌ๋Ÿฌ ๊ฐœ์˜ ์นผ๋Ÿผ์„ ๊ฒฐํ•ฉํ•ด์„œ ๋งŒ๋“ค ์ˆ˜ ์žˆ๋‹ค. ์ตœ๋Œ€ 32๊ฐœ์˜ ์ปฌ๋Ÿผ๊นŒ์ง€ ํ—ˆ์šฉํ•œ๋‹ค. ์ด ์กฐํ•ฉ์„ ํ˜„๋ช…ํ•˜๊ฒŒ ํ•ด์„œ ํ…Œ์ด๋ธ”์˜ ์•ก์„ธ์Šค, ์ธ๋ฑ์Šค ์Šค์บ” ์ตœ์†Œํ™”์— ํ™œ์šฉํ•  ์ˆ˜ ์žˆ๋‹ค. ์šฐ๋ฆฌ๊ฐ€ ์ฃผ๋ชฉํ•ด์•ผ ํ•  ๊ฒƒ์€ ์ฒซ ๋ฒˆ์งธ๋กœ Random I/O๋ฅผ ์ค„์ด๊ณ , ์ถฉ๋ถ„ํžˆ ์ค„์˜€๋‹ค๋ฉด ์ˆ˜ํ‰ ํƒ์ƒ‰์„ ์ค„์ด๋Š” ๋ฐฉํ–ฅ์œผ๋กœ์˜ ํŠœ๋‹์ด ํ•„์š”ํ•˜๋‹ค.

์˜ˆ๋ฅผ ๋“ค์–ด ์•„๋ž˜์™€ ๊ฐ™์€ SQL์„ ์ˆ˜ํ–‰ํ•œ๋‹ค๊ณ  ๊ฐ€์ •ํ•ด ๋ณด์ž.

SELECT ์‚ฌ๋ฒˆ
FROM ์‚ฌ์›
WHERE ์‚ฌ์›๋ช… = '์กฐํฌ์ˆ˜'
AND ์ง๊ธ‰ = '๋ถ€์žฅ';

์ธ๋ฑ์Šค๊ฐ€ ์ด๋ฆ„์œผ๋กœ๋งŒ ๋˜์–ด ์žˆ๋Š” ์ƒํƒœ์ผ ๋•Œ, ์กฐํฌ์ˆ˜ ๊ณผ์žฅ๊ณผ ์กฐํฌ์ˆ˜ ๋ถ€์žฅ์ด ์กด์žฌํ•œ๋‹ค๋ฉด, ์ธ๋ฑ์Šค๋กœ ๋‘ ๊ฐœ์˜ ์กฐํฌ์ˆ˜๋ฅผ ์ฐพ๊ณ  ๊ณผ์žฅ๊ณผ ๋ถ€์žฅ์œผ๋กœ ๋‘ ๋ฒˆ์˜ Random I/O๊ฐ€ ์ผ์–ด๋‚œ๋‹ค. ํ•˜์ง€๋งŒ ์• ์ดˆ์— ์ธ๋ฑ์Šค์— (์‚ฌ์›๋ช…, ์ง๊ธ‰)์œผ๋กœ ๊ฒฐํ•ฉ ์ธ๋ฑ์Šค๋ฅผ ์ƒ์„ฑํ•ด ๋‘”๋‹ค๋ฉด, ํ•œ ๋ฒˆ์— ์กฐํฌ์ˆ˜ ๋ถ€์žฅ์„ ์ฐพ์•„์„œ Random I/O๋Š” ํ•œ ๋ฒˆ๋งŒ ์ผ์–ด๋‚œ๋‹ค.

์ด๋•Œ ๊ฒฐํ•ฉ ์ธ๋ฑ์Šค์—์„œ ์ธ๋ฑ์Šค์˜ ์„ ํ–‰ ์ปฌ๋Ÿผ์ด ์กฐ๊ฑด์ ˆ์— ์—†๊ฑฐ๋‚˜ โ€˜=โ€™ ์กฐ๊ฑด์ด ์•„๋‹ˆ๋ฉด ์ธ๋ฑ์Šค ์Šค์บ”์˜ ํšจ์œจ์„ฑ์ด ๋‚ฎ์•„์ง‘๋‹ˆ๋‹ค. ์ฒซ ์„ ๋ถ„ ์กฐ๊ฑด ์ปฌ๋Ÿผ๊นŒ์ง€๋งŒ ์—ฐ์†์  ์Šค์บ”์ด ๊ฐ€๋Šฅํ•˜๋ฏ€๋กœ ์ดํ›„ ์ปฌ๋Ÿผ์— ๋Œ€ํ•œ ์กฐ๊ฑด์€ ์Šค์บ”์˜ ๋ฒ”์œ„๋ฅผ ์ค„์—ฌ ์ฃผ์ง€ ๋ชปํ•˜๊ณ  FILTER ์กฐ๊ฑด์œผ๋กœ๋งŒ ์ฐธ์—ฌํ•˜๊ฒŒ ๋œ๋‹ค. ๋”ฐ๋ผ์„œ ๊ฒฐํ•ฉ ์ธ๋ฑ์Šค ์ƒ์„ฑ์‹œ WHERE ์ ˆ์—์„œ ํ•ญ์ƒ ์‚ฌ์šฉํ•˜๋Š” ์ปฌ๋Ÿผ์ด๋‚˜ โ€˜=โ€™ ์กฐ๊ฑด์„ ๋งŽ์ด ์‚ฌ์šฉํ•˜๋Š” ์ปฌ๋Ÿผ์„ ์•ž์— ๋‘˜์ˆ˜๋ก ์ข‹๋‹ค.

PLAN_TABLE_OUTPUT
------------------------------------------------------------------------------------------------------------------------------------------------------
SQL_ID  b5p87f5czvjh7, child number 0
-------------------------------------
SELECT /*+ index(emp2 emp2_x01) */ * FROM EMP2 WHERE DEPTNO=30 AND
SAL>=2000

Plan hash value: 3451918632

--------------------------------------------------------------------------------------------------
| Id  | Operation                   | Name     | Starts | E-Rows | A-Rows |   A-Time   | Buffers |
--------------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT            |          |      1 |        |   8192 |00:00:00.02 |    2339 |
|*  1 |  TABLE ACCESS BY INDEX ROWID| EMP2     |      1 |  30492 |   8192 |00:00:00.02 |    2339 |
|*  2 |   INDEX RANGE SCAN          | EMP2_X01 |      1 |  38229 |  49152 |00:00:00.01 |     238 |
--------------------------------------------------------------------------------------------------

Predicate Information (identified by operation id):
---------------------------------------------------

   1 - filter("SAL">=2000)
   2 - access("DEPTNO"=30)

21 rows selected.

emp2_x01 ์ธ๋ฑ์Šค๋ฅผ ์‚ฌ์šฉํ•œ ์Šค์บ”์€ ์ธ๋ฑ์Šค ์Šค์บ”์—์„œ 238๋ฒˆ์˜ I/O, ๊ทธ๋ฆฌ๊ณ  Random I/O๋ฅผ 2000๋ฒˆ ํ•œ ๊ฒƒ์„ ํ™•์ธํ•  ์ˆ˜ ์žˆ๋‹ค.

PLAN_TABLE_OUTPUT
------------------------------------------------------------------------------------------------------------------------------------------------------
SQL_ID  67cz5fd95du3u, child number 0
-------------------------------------
SELECT /*+ index(emp2 emp2_new) */* FROM EMP2 WHERE DEPTNO=30 AND
SAL>=2000

Plan hash value: 2378551592

-----------------------------------------------------------------------------------------------------------
| Id  | Operation                   | Name     | Starts | E-Rows | A-Rows |   A-Time   | Buffers | Reads  |
-----------------------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT            |          |      1 |        |   8192 |00:00:00.01 |     854 |     22 |
|   1 |  TABLE ACCESS BY INDEX ROWID| EMP2     |      1 |  30492 |   8192 |00:00:00.01 |     854 |     22 |
|*  2 |   INDEX RANGE SCAN          | EMP2_NEW |      1 |  30492 |   8192 |00:00:00.01 |     104 |     22 |
-----------------------------------------------------------------------------------------------------------

Predicate Information (identified by operation id):
---------------------------------------------------

   2 - access("DEPTNO"=30 AND "SAL">=2000 AND "SAL" IS NOT NULL)

20 rows selected.

์ด๋•Œ INDEX(DEPTNO, SAL)์„ ์ƒˆ๋กœ ์„ค์ •ํ•ด ํŠœ๋‹ํ•ด ์ฃผ๋ฉด, ์ธ๋ฑ์Šค ์Šค์บ”์—์„œ 104๋ฒˆ์œผ๋กœ ๊ฑฐ๋ฅผ ์ˆ˜ ์žˆ์œผ๋ฉฐ, Random I/O๊ฐ€ 850๋ฒˆ์œผ๋กœ ํ™• ์ค„์–ด๋“  ๊ฒƒ์„ ํ™•์ธํ•  ์ˆ˜ ์žˆ๋‹ค. ๋˜ํ•œ ์ด๋ฏธ ์ธ๋ฑ์Šค์— SAL ์นผ๋Ÿผ์ด ๋ฐ˜์˜๋˜์–ด ์žˆ๊ธฐ ๋•Œ๋ฌธ์— ์ธ๋ฑ์Šค ์Šค์บ” ์ดํ›„ ๋”ฐ๋กœ FILTERING์ด ๋ถˆํ•„์š”ํ•˜๋‹ค.

Index Inlist Iterator

QUERY์— ๊ฐ’์„ ๊ฐ€์ง„ IN์ ˆ์ด๋‚˜ ๋™์ผํ•œ ์—ด์— ๋“ฑ์‹ ์ˆ ์–ด๊ฐ€ OR๋กœ ์—ฐ๊ฒฐ๋˜์–ด ์žˆ์„ ๋–„ ์‚ฌ์šฉ๋œ๋‹ค. INLIST ITERATOR๋Š” ์—ด๊ฑฐ๋œ ๊ฐ’๋“ค์„ ๋ณ„๋„๋กœ ์‹คํ–‰ํ•œ๋‹ค. ์‹คํ–‰ ๊ณ„ํš์€ ๋“ฑ์‹ ์ ˆ์„ ๊ฐ€์ง„ ๋ช…๋ น๋ฌธ์˜ ๊ฒฐ๊ณผ์™€ ๋™์ผํ•˜๋ฉฐ ๋‹จ๊ณ„๊ฐ€ ํ•˜๋‚˜ ์ถ”๊ฐ€๋œ๋‹ค.

์˜ตํ‹ฐ๋งˆ์ด์ €๋Š” IN์ ˆ์— ๊ฐ’์ด ์ง€์ •๋  ๋•Œ INLIST ITERATOR๋ฅผ ์‚ฌ์šฉํ•˜๊ณ , ํ•ด๋‹น ์—ด์— ๋Œ€ํ•œ ์„ ํƒ์  ์ธ๋ฑ์Šค๋ฅผ ์ฐพ๋Š”๋‹ค. ๋™์ผํ•œ ์ธ๋ฑ์Šค๋ฅผ ์‚ฌ์šฉํ•˜๋Š” OR ์ ˆ์ด ์žˆ๋Š” ๊ฒฝ์šฐ ์˜ตํ‹ฐ๋งˆ์ด์ €๋Š” ์ด ์—ฐ์‚ฐ์„ ์„ ํƒํ•œ๋‹ค. IN ์—ฐ์‚ฐ์ž๋กœ ์ž‘์„ฑํ•œ ๊ฐ’์ด ๋งค์šฐ ๋งŽ๊ณ  ์ด๋ฏธ ๊ฐ€๊นŒ์ด ์žˆ๋Š” ๊ทผ์ ‘๊ฐ’์ด๋ผ๋ฉด ์ธ๋ฑ์Šค๋ฅผ ๊ฐ๊ฐ ํƒ€๋Š” ๊ฒƒ๋ณด๋‹ค ๋ฒ”์œ„ ์„ ํƒ ํ›„ ํ•„ํ„ฐ๋งํ•˜๋Š” ๊ฒƒ์ด ๋” ๋‚˜์„ ์ˆ˜๋„ ์žˆ๋‹ค. IN ์—ฐ์‚ฐ์ž๋Š” ๊ฐ’๋“ค์ด ์—ฌ๊ธฐ์ €๊ธฐ ํฉ์–ด์ ธ ์žˆ์„ ๊ฒฝ์šฐ ๋ฒ”์œ„ ์Šค์บ”์˜ ๋น„์šฉ์„ ์ค„์ด๊ธฐ ์œ„ํ•ด ์„ ํƒํ•œ๋‹ค๊ณ  ๋ณด๋ฉด ๋œ๋‹ค.

Index Full Scan

๋ชจ๋“  leaf block์„ logical ์ˆœ์„œ๋Œ€๋กœ ์ฝ๋Š” ๊ฒƒ์ด๋‹ค. ์ธ๋ฑ์Šค ์ปฌ๋Ÿผ ์ด์™ธ์˜ ์ปฌ๋Ÿผ ์กฐํšŒ ์‹œ์—๋„ ์‚ฌ์šฉ๋  ์ˆ˜ ์žˆ์œผ๋ฉฐ, ์‚ฌ์šฉ๋˜๋Š” ์ปฌ๋Ÿผ์˜ NOT NULL ์ œ์•ฝ ์กฐ๊ฑด ๋˜๋Š” ์กฐ๊ฑด์‹์ด ํ•„์š”ํ•˜๋‹ค. Left Most Child๋ฅผ ์ฐพ๊ธฐ ์œ„ํ•ด Root์™€ Branch๋ฅผ ํ•œ ๋ฒˆ์”ฉ ๋ฐฉ๋ฌธํ•œ๋‹ค. Multi Block์ด ์•„๋‹Œ ์ฐจ๋ก€์ฐจ๋ก€๋กœ ์ฝ์–ด ์˜ค๋Š” ๋ฐฉ์‹์ด๋‹ค. ์ธ๋ฑ์Šค์— ๋”ฐ๋ผ ์ €์žฅ๋œ ๋ฐ์ดํ„ฐ๋“ค์ด ๋ฌผ๋ฆฌ์ ์œผ๋กœ ์˜†์— ์žˆ์ง€ ์•Š๊ธฐ ๋•Œ๋ฌธ์—, ๋…ผ๋ฆฌ์ ์ธ B+ Tree ๊ตฌ์กฐ์— ๋”ฐ๋ผ ๋˜‘๊ฐ™์ด ROWID๋ฅผ ์ฐพ์•„ ๋ถˆ๋Ÿฌ์˜ค๋Š” ํ˜•์‹์ด๋‹ค. ๋”ฐ๋ผ์„œ Single Block I/O๋ฅผ ์‹คํ–‰ํ•œ๋‹ค. ๋ณดํ†ต Full Table Scan ๋Œ€์‹  ํ˜น์€ SORT ๋Œ€์‹ ์œผ๋กœ ์‚ฌ์šฉํ•œ๋‹ค.

Index Fast Full Scan

๋ชจ๋“  Leaf Block์„ ์ฝ๋Š”๋‹ค. ์ธ๋ฑ์Šค์— ํฌํ•จ๋œ ์ปฌ๋Ÿผ์œผ๋กœ๋งŒ ์กฐํšŒํ•  ๋•Œ ์‚ฌ์šฉํ•œ๋‹ค. ์ด๊ฒƒ ์—ญ์‹œ ์‚ฌ์šฉ๋˜๋Š” ์นผ๋Ÿผ์— NOT NULL ์ œ์•ฝ ์กฐ๊ฑด ๋˜๋Š” ์กฐ๊ฑด์‹์ด ํ•„์š”ํ•˜๊ณ , Multi Block Read๋ฅผ ์ˆ˜ํ–‰ํ•˜๊ธฐ ๋•Œ๋ฌธ์— ๋น ๋ฅธ ์ฝ๊ธฐ๊ฐ€ ๊ฐ€๋Šฅํ•ด์ง„๋‹ค. ๋ณ‘๋ ฌ ์ฒ˜๋ฆฌ๊ฐ€ ๊ฐ€๋Šฅํ•˜๊ณ , ๋„“์€ ๋ฒ”์œ„์˜ ๊ฒ€์ƒ‰์—์„œ ์‚ฌ์šฉ๋œ๋‹ค.

Index Join Scan

์ธ๋ฑ์Šค๋ผ๋ฆฌ ์กฐ์ธ๋˜๋Š” ํ˜•ํƒœ์ด๋ฉฐ SELECT ์ ˆ๊ณผ WHERE ์ ˆ ์นผ๋Ÿผ์ด ๋ชจ๋‘ ์ธ๋ฑ์Šค์— ์กด์žฌํ•ด์•ผ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๋‹ค. ํ…Œ์ด๋ธ”์˜ ์ ‘๊ทผ ์—†์ด ์ธ๋ฑ์Šค๋งŒ ์ด์šฉ ๊ฐ€๋Šฅํ•  ๊ฒฝ์šฐ ์‚ฌ์šฉ๋œ๋‹ค. HASH JOIN์˜ ํ˜•ํƒœ๋กœ ๋™์ž‘ํ•œ๋‹ค. ROWID๊ฐ€ ๊ฐ™์€ ๋ฐ์ดํ„ฐ๋“ค๋ผ๋ฆฌ JOINํ•œ๋‹ค๊ณ  ์ƒ๊ฐํ•˜๋ฉด ๋œ๋‹ค.

SORT ORDER BY

SORT ORDER BY ์‹คํ–‰ ๋‹จ๊ณ„๋Š” Sort Area๋ฅผ ํ• ๋‹นํ•˜์—ฌ ์ •๋ ฌ ์ž‘์—…์„ ์ˆ˜ํ–‰ํ•œ๋‹ค. ์ •๋ ฌ ์ƒํƒœ๋ฅผ ์ด๋ฏธ ๊ฐ€์ง€๊ณ  ์žˆ๋Š” ์ธ๋ฑ์Šค๊ฐ€ ์žˆ๋‹ค๋ฉด, ๋ณ„๋„์˜ ์ •๋ ฌ ์ž‘์—… ์ˆ˜ํ–‰ ์—†์ด ๊ทธ๋ƒฅ ๊ฒ€์ƒ‰ํ•  ์ˆ˜ ์žˆ๋‹ค. ๋”ฐ๋ผ์„œ ์ธ๋ฑ์Šค๋ฅผ ์ ์ ˆํ•˜๊ฒŒ ํ™œ์šฉํ•˜๋ฉด ์ •๋ ฌํ•˜๋Š” ์ž‘์—…์— ๋Œ€ํ•œ ํฐ ์ด๋“์„ ๋ณผ ์ˆ˜ ์žˆ๋‹ค. ํ•˜์ง€๋งŒ ์ •๋ ฌ์„ ์ˆ˜ํ–‰ํ•˜๋Š” ๊ฒƒ์ด ๋” ๋‚˜์€ ๊ฒฝ์šฐ๋„ ์žˆ๊ธฐ ๋•Œ๋ฌธ์— ์ฃผ์˜ ๊นŠ๊ฒŒ ์‚ฌ์šฉํ•ด์•ผ ํ•œ๋‹ค.

์ด๋•Œ ์กฐ๊ฑด์ ˆ์„ ์ด์šฉํ•˜์—ฌ NOT NULL์ธ ๊ฐ’๋“ค๋งŒ ์•ก์„ธ์Šคํ•˜๋„๋ก ํ•ด์•ผ ์ธ๋ฑ์Šค๋ฅผ ์ด์šฉํ•œ ์ •๋ ฌ ์ž‘์—…์„ ์ˆ˜ํ–‰ํ•  ์ˆ˜ ์žˆ๋‹ค. ๊ทธ๋ƒฅ ์ •๋ ฌ์„ ํ•  ๋•Œ๋Š” NULL ๊ฐ’์€ ๊ฐ€์žฅ ํฐ ๊ฐ’์ด๋ผ๊ณ  ๊ฐ€์ •ํ•˜๊ณ  ์ •๋ ฌํ•œ๋‹ค. ํ•˜์ง€๋งŒ B+ Tree Index์—๋Š” NULL ๊ฐ’์ด ์•ˆ ๋“ค์–ด๊ฐ€ ์žˆ๊ธฐ ๋•Œ๋ฌธ์— ์ธ๋ฑ์Šค๋ฅผ ์ด์šฉํ•œ ์ •๋ ฌ์„ ํ•  ๋•Œ๋Š” ์ฃผ์˜ํ•ด์•ผ ํ•œ๋‹ค. ๋˜ํ•œ ๊ธฐ์กด์˜ ์ •๋ ฌ ์ž‘์—…์€ ๋ชจ๋“  ๋ฐ์ดํ„ฐ๋ฅผ ์ •๋ ฌํ•ด์•ผ ํ•ด์„œ ๋ถ€๋ถ„ ๋ฒ”์œ„ ์ฒ˜๋ฆฌ๊ฐ€ ๋ถˆ๊ฐ€๋Šฅํ•˜์ง€๋งŒ, ์ธ๋ฑ์Šค๋ฅผ ์‚ฌ์šฉํ•˜๋ฉด ์ •๋ ฌ ์ž‘์—… ์ž์ฒด๊ฐ€ ์ƒ๋žต๋˜๊ธฐ ๋•Œ๋ฌธ์— ๋ถ€๋ถ„ ๋ฒ”์œ„ ์ฒ˜๋ฆฌ๊ฐ€ ๊ฐ€๋Šฅํ•˜๋‹ค. ๋”ฐ๋ผ์„œ ์œ ์ €๋Š” ๋”์šฑ ๋น ๋ฅด๊ฒŒ ์‘๋‹ต์„ ๋ฐ›์•„ ๋ณผ ์ˆ˜ ์žˆ๋‹ค.

์ธ๋ฑ์Šค ์Šค์บ”์„ ๋ชป ํ•˜๋Š” ๊ฒฝ์šฐ

  • <> , !=, ^= ๋“ฑ ๋ถ€์ •ํ˜• ๋น„๊ต ๋ถ€์ •ํ˜• ๋น„๊ต๋Š” ํŠน์ •๊ฐ’์„ ์ œ์™ธํ•œ ๋‚˜๋จธ์ง€ ๋ชจ๋“  ๊ฐ’์„ ๋น„๊ตํ•ด์•ผ ํ•˜๋Š” ์ƒํ™ฉ์ด๊ธฐ ๋•Œ๋ฌธ์— ์ธ๋ฑ์Šค์˜ ๊ฒ€์ƒ‰ ๋ฒ”์œ„๊ฐ€ ๋„“์–ด์งˆ ์ˆ˜ ์žˆ์–ด์„œ ์ธ๋ฑ์Šค ์‚ฌ์šฉ์ด ๋ถˆ๊ฐ€๋Šฅํ•œ ๊ฒฝ์šฐ๊ฐ€ ๋งŽ๋‹ค.
  • ์ธ๋ฑ์Šค ์ปฌ๋Ÿผ์˜ ๋ณ€ํ˜•์ด ๋ฐœ์ƒํ•œ ๊ฒฝ์šฐ ์ธ๋ฑ์Šค๋Š” ์ปฌ๋Ÿผ์— ์ €์žฅ๋˜์–ด ์žˆ๋Š” ๊ฐ’์œผ๋กœ ์ •๋ ฌ๋˜์–ด ์žˆ๊ธฐ ๋•Œ๋ฌธ์— ๊ณ„์‚ฐ, ๋ณ€ํ˜•ํ•˜๋Š” ๊ฒฝ์šฐ ์ธ๋ฑ์Šค๋ฅผ ์‚ฌ์šฉํ•  ์ˆ˜ ์—†๋‹ค. (ex TO_CHAR(sal))
  • LIKE โ€˜%๋ฌธ์ž์—ดโ€™ ์‹œ์ž‘๋˜๋Š” ๋ฌธ์ž์—ด์„ ๋ชจ๋ฅด๋ฉด ์ธ๋ฑ์Šค์˜ ์Šค์บ” ์‹œ์ž‘ ๋ถ€๋ถ„์„ ์ฐพ์„ ์ˆ˜ ์—†๊ธฐ ๋•Œ๋ฌธ์— Table Full Scan์ด ์‚ฌ์šฉ๋˜๊ฑฐ๋‚˜ Index Full Scan์„ ์‚ฌ์šฉํ•  ์ˆ˜๋ฐ–์— ์—†๋‹ค.
  • IS NULL (B+ Tree์— ์—†์Œ) B+ Tree ์ธ๋ฑ์Šค๋Š” NULL ๊ฐ’์„ ์ €์žฅํ•˜์ง€ ์•Š๊ธฐ ๋•Œ๋ฌธ์— IS NULL ์—ฐ์‚ฐ์ž๋Š” ์ธ๋ฑ์Šค๋ฅผ ํ•ญ์ƒ ์‚ฌ์šฉํ•  ์ˆ˜ ์—†๋‹ค. NULL ๊ฐ’์ด ๋Œ€๋Ÿ‰์œผ๋กœ ๋“ค์–ด ์žˆ์–ด์„œ ์ธ๋ฑ์Šค๋ฅผ ์‚ฌ์šฉํ•˜์ง€ ์•Š์•„๋„ ๋˜๋Š” ๊ฒฝ์šฐ๊ฐ€ ์•„๋‹ˆ๋ผ ์†Œ๋Ÿ‰์˜ NULL์„ ๊ฒ€์ƒ‰ํ•ด์•ผ ํ•œ๋‹ค๋ฉด DEFAULT ๊ฐ’์œผ๋กœ ๋Œ€์ฒดํ•˜๊ฑฐ๋‚˜ Function Based Index๋ฅผ ํ•˜๋Š” ๋“ฑ์˜ ์šฐํšŒ์ ์ธ ๋ฐฉ๋ฒ•์ด ํ•„์š”ํ•˜๋‹ค.
  • ๊ฐ€๊ณตํ•˜์ง€ ์•Š์€ ์„ ํ–‰ ์ปฌ๋Ÿผ์ด ์กฐ๊ฑด์ ˆ์— ์—†์„ ๋•Œ

์กฐ์ธ ํŠœ๋‹

Nested Loops Join

Nested Loops Join

Outer Table ํ–‰์˜ ์†Œ์Šค๋ฅผ ์Šค์บ”ํ•˜๋Š” ๊ฒƒ์ด๋‹ค. Outer Table์˜ ๊ฐ ํ–‰์— ๋Œ€ํ•ด ์กฐ์ธ ์กฐ๊ฑด์„ ๋งŒ์กฑํ•˜๋Š” Inner Table์˜ ๋ชจ๋“  ํ–‰์„ ๊ฒ€์ƒ‰ํ•˜๋Š” ๊ฒƒ์ด๋‹ค. Outer Table ๊ฒ€์ƒ‰ ์กฐ๊ฑด์˜ ํ–‰์ด ์ ์„ ๊ฒฝ์šฐ์— ์ ํ•ฉํ•˜๊ณ  ์กฐ์ธ์— ์ฐธ์—ฌํ•˜๋Š” ํ…Œ์ด๋ธ”์˜ ์ˆœ์„œ๊ฐ€ ์ค‘์š”ํ•˜๋‹ค.

Nested Loops Join์€ ์„ ํ–‰ ํ…Œ์ด๋ธ” (Outer Table - driving) ๊ฒฐ์ • ํ›„ ํ›„ํ–‰ ํ…Œ์ด๋ธ” (Inner Table - driven)์— ๋ฐ˜๋ณต์ ์œผ๋กœ ์ ‘๊ทผํ•œ๋‹ค. ํ›„ํ–‰ ํ…Œ์ด๋ธ”์˜ ์กฐ์ธ ์ปฌ๋Ÿผ์— ์ธ๋ฑ์Šค๊ฐ€ ํ•„์š”ํ•˜๊ณ , ์†Œ๋Ÿ‰์˜ ๋ฐ์ดํ„ฐ๋ฅผ ์กฐ์ธํ•˜๋Š” OLTP ์—…๋ฌด ํ™˜๊ฒฝ์— ์ ํ•ฉํ•˜๋‹ค. ํ•œ ๋ ˆ์ฝ”๋“œ์”ฉ ์ˆœ์ฐจ์ ์œผ๋กœ ์ฒ˜๋ฆฌํ•˜๊ธฐ ๋•Œ๋ฌธ์— ๋ถ€๋ถ„ ๋ฒ”์œ„ ์ฒ˜๋ฆฌ์— ์ตœ์ ํ™”๋˜์–ด ์žˆ๋‹ค. ๋งŽ์€ ์–‘์˜ ๋ฐ์ดํ„ฐ๋ฅผ ์กฐ์ธํ•  ๋•Œ Random Access ํšŸ์ˆ˜๊ฐ€ ๋†’์•„์ง„๋‹ค. ๋”ฐ๋ผ์„œ Nested Loops Join์˜ ํŠœ๋‹ ํฌ์ธํŠธ๋Š” Index ํŠœ๋‹ ํฌ์ธํŠธ๋ž‘ ๋™์ผํ•˜๋‹ค.

์„ ํ–‰, ํ›„ํ–‰ ํ…Œ์ด๋ธ”์„ ๊ฒฐ์ •ํ•˜๋Š” ์กฐ๊ฑด์€ ๋‹ค์Œ๊ณผ ๊ฐ™๋‹ค.

  1. 1๊ฑด ๊ฑธ๋Ÿฌ๋‚ด๋Š” ์กฐ๊ฑด์ด ์žˆ๋Š” ํ…Œ์ด๋ธ”์ด ์„ ํ–‰ ํ…Œ์ด๋ธ”
  2. ์กฐ์ธ ์กฐ๊ฑด ์ปฌ๋Ÿผ์— ์ธ๋ฑ์Šค๊ฐ€ ์žˆ๋Š” ๊ฒƒ์ด ํ›„ํ–‰ ํ…Œ์ด๋ธ” (Random Access ์ตœ์†Œํ™”)
  3. ์–‘์ชฝ์— ์ธ๋ฑ์Šค๊ฐ€ ์žˆ๊ณ  ์ถ”๊ฐ€ ์กฐ๊ฑด์ด ์žˆ๋‹ค๋ฉด ์ถ”๊ฐ€ ์กฐ๊ฑด์ด ์žˆ๋Š” ์ชฝ์ด ์„ ํ–‰ ํ…Œ์ด๋ธ”

์‹คํ–‰ ๊ณ„ํš์—์„œ๋Š” Outer Table - Inner Table ์ˆœ์„œ๋กœ ๋‚˜์˜จ๋‹ค.

NLJ Batching

๋งŒ์•ฝ ์กฐ์ธํ•˜๋ ค๋Š” ๋ฐ์ดํ„ฐ๊ฐ€ ๋ฒ„ํผ ์บ์‹œ์— ์—†์œผ๋ฉด ๊ณ„์†ํ•ด์„œ ๋ฌผ๋ฆฌ์  ์ฝ๊ธฐ๋ฅผ ์‹œ๋„ํ•ด์•ผ ํ•˜๊ธฐ ๋•Œ๋ฌธ์— ์„œ๋ฒ„๊ฐ€ I/O ์‘๋‹ต์„ ์–ป์„ ๋•Œ๊นŒ์ง€ Sleepํ•ด์•ผ ํ•˜๋Š” ์‹œ๊ฐ„์ด ๋งŽ๋‹ค. ๋”ฐ๋ผ์„œ ์ผ๋‹จ ๋ฒ„ํผ ์บ์‹œ์— ์žˆ๋Š” ๋ฐ์ดํ„ฐ๋ผ๋ฆฌ๋งŒ ์ผ๋‹จ JOIN์„ ํ•˜๊ณ , ๋ฒ„ํผ ์บ์‹œ์— ์—†์–ด์„œ ์กฐ์ธ์„ ๋ณด๋ฅ˜ํ•œ ๋ฐ์ดํ„ฐ๋“ค์„ ๋ชจ์•„๋‹ค๊ฐ€ ํ•œ ๋ฒˆ์— ๋ฌผ๋ฆฌ์  ์ฝ๊ธฐ๋ฅผ ์‹œ๋„ํ•˜๋Š” ๊ฒƒ์ด NLJ Batching์ด๋‹ค.

Sort Merge Join

Sort Merge Join

์ฒซ ๋ฒˆ์งธ์™€ ๋‘ ๋ฒˆ์งธ ํ–‰ ์†Œ์Šค๊ฐ€ ๋™์ผํ•œ ์ •๋ ฌ ํ‚ค๋กœ ์ •๋ ฌ๋˜๊ณ , ์–‘ ์ชฝ์—์„œ ์ •๋ ฌ๋œ ํ–‰์ด ๋ณ‘ํ•ฉ๋˜๋Š” ๊ฒƒ์ด๋‹ค. ์ž‘์—… ์ˆœ์„œ๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™๋‹ค.

  1. ์ฒซ ๋ฒˆ์งธ ๋ฐ์ดํ„ฐ ์ง‘ํ•ฉ์„ ๊ฐ€์ ธ์™€์„œ ์กฐ์ธ ์ปฌ๋Ÿผ์— ๋Œ€ํ•ด ์ •๋ ฌ
  2. ๋‘ ๋ฒˆ์งธ ๋ฐ์ดํ„ฐ ์ง‘ํ•ฉ์„ ๊ฐ€์ ธ์™€์„œ ์กฐ์ธ ์ปฌ๋Ÿผ์— ๋Œ€ํ•ด ์ •๋ ฌ
  3. ์ฒซ ๋ฒˆ์งธ ๋ฐ์ดํ„ฐ ์ง‘ํ•ฉ์˜ ๊ฐ ํ–‰์— ๋Œ€ํ•ด์„œ ๋‘ ๋ฒˆ์งธ ๋ฐ์ดํ„ฐ ์ง‘ํ•ฉ์—์„œ ์‹œ์ž‘์ ์„ ์ฐพ๊ณ  ์กฐ์ธํ•˜์ง€ ์•Š๋Š” ํ–‰์„ ์ฐพ์„ ๋•Œ๊นŒ์ง€ ์ˆ˜ํ–‰

ํ•ฉ๋ณ‘ํ•ด์•ผ ํ•˜๊ธฐ ๋•Œ๋ฌธ์— ์กฐ์ธ ์ž‘์—…์ด ์™„๋ฃŒ๋˜๊ธฐ๊นŒ์ง€ ๋ถ€๋ถ„ ๋ฒ”์œ„ ์ฒ˜๋ฆฌ๊ฐ€ ๋ถˆ๊ฐ€๋Šฅํ•˜๋‹ค. ์–‘์ชฝ ๋ชจ๋‘ ์ •๋ ฌ์ด ๋๋‚˜์•ผ์ง€๋งŒ ์กฐ์ธ์ด ๋งŒ๋“ค์–ด์ง€๊ธฐ ๋•Œ๋ฌธ์ด๋‹ค. ์ „์šฉ์˜ ๋ฉ”๋ชจ๋ฆฌ ๊ณต๊ฐ„์ธ PGA์—์„œ ์ˆ˜ํ–‰๋˜๊ธฐ ๋•Œ๋ฌธ์— ์†๋„๊ฐ€ ๋น ๋ฅด๋‚˜, ์ถฉ๋ถ„ํ•œ ๋ฉ”๋ชจ๋ฆฌ ํ™•๋ณด๊ฐ€ ์ด๋ฃจ์–ด์ง€์ง€ ์•Š์œผ๋ฉด ์ž„์‹œ ํ…Œ์ด๋ธ” ์ŠคํŽ˜์ด์Šค๋ฅผ ํ™œ์šฉํ•˜๊ธฐ ๋•Œ๋ฌธ์— ์„ฑ๋Šฅ ์ €ํ•˜์˜ ์›์ธ์ด ๋  ์ˆ˜๋„ ์žˆ๋‹ค. ๊ทธ๋Ÿผ์—๋„ ๋ถˆ๊ตฌํ•˜๊ณ  ์ด ์กฐ์ธ์ด ๋งŽ์ด ํ™œ์šฉ๋  ๋•Œ๋Š”, ์ด๋ฏธ ์ธ๋ฑ์Šค๊ฐ€ ์žˆ์–ด์„œ SORT ์—†์ด MERGE๋งŒ ํ•ด๋„ ๋  ๋•Œ ์„ ํƒ๋  ์ˆ˜ ์žˆ๋‹ค. ๋‘˜ ๋‹ค ์ •๋ ฌํ•˜๊ณ  ์กฐ์ธํ•˜๋Š” ๊ฒฝ์šฐ๋Š” ๋Œ€์šฉ๋Ÿ‰ DB์—์„œ๋Š” ๊ฑฐ์˜ ๋ณผ ์ˆ˜ ์—†๋‹ค.

Hash Join

Hash Join

์ž‘์€ ํ–‰ ์†Œ์Šค (Build Table)๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ํ•ด์‹œ ๋งต์„ ์ƒ์„ฑํ•œ๋‹ค. ๋‘ ๋ฒˆ์จฐ ํ–‰ ์†Œ์Šค (Probe Table)์ด ํ•ด์‹ฑ ์ฒ˜๋ฆฌ๋˜์–ด ํ•ด์‹œ ๋งต์— ๋Œ€ํ•ด ๊ฒ€์‚ฌํ•œ๋‹ค. ์ž‘์—… ์ˆœ์„œ๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™๋‹ค.

  1. ํฌ๊ธฐ๊ฐ€ ์ž‘์€ ํ…Œ์ด๋ธ”์„ Build Table๋กœ ๊ฒฐ์ • ํ›„ ํ•ด์‹œ๋งต์„ PGA์˜ Hash Area์— ์ƒ์„ฑํ•œ๋‹ค.
  2. ํฌ๊ธฐ๊ฐ€ ํฐ ํ…Œ์ด๋ธ”์„ Probe Table๋กœ ์•ก์„ธ์Šคํ•˜์—ฌ ์กฐ์ธํ•œ๋‹ค.

์ด๋Š” ํ•ด์‹œ๋ฐ์ดํ„ฐ๋ฅผ ํ™œ์šฉํ•œ ์กฐ์ธ์ด๊ธฐ ๋•Œ๋ฌธ์— = ์กฐ์ธ์—์„œ๋งŒ ์‚ฌ์šฉ์ด ๊ฐ€๋Šฅํ•˜๊ณ , ์ „์ฒด ๋ฒ”์œ„ ์ฒ˜๋ฆฌ์— ์ตœ์ ํ™”๋˜์–ด ์žˆ๋‹ค. ์†Œ๋Ÿ‰์˜ ๋ฐ์ดํ„ฐ๋ฅผ ์‚ฌ์šฉํ•  ๋•Œ ์“ฐ์ธ๋‹ค๋ฉด ๋ถˆํ•„์š”ํ•œ I/O๊ฐ€ ์ฆ๊ฐ€ํ•˜์—ฌ ์˜คํžˆ๋ ค ๋น„ํšจ์œจ์ ์ผ ์ˆ˜ ์žˆ๋‹ค. Hash Join์€ ๋Œ€๋Ÿ‰์˜ ์กฐ์ธ์„ ์ˆ˜ํ–‰ํ•  ๋•Œ ์‚ฌ์šฉ๋˜๊ธฐ ๋•Œ๋ฌธ์— ๊ฐ€๊ธ‰์ ์œผ๋กœ Multi Block I/O๋ฅผ ์ง€์›ํ•˜๋Š” ์•ก์„ธ์Šค ๋ฐฉ๋ฒ•์„ ์‚ฌ์šฉํ•œ๋‹ค. ์กฐ์ธ ์ˆœ์„œ์— ๋”ฐ๋ผ I/O์˜ ๋ณ€ํ™”๋Š” ์—†์œผ๋‚˜ ์‚ฌ์šฉ๋œ ๋ฉ”๋ชจ๋ฆฌ์˜ ํฌ๊ธฐ๊ฐ€ ๋ˆˆ์— ๋„๊ฒŒ ์ฆ๊ฐ€๋œ ๊ฒƒ์„ ํ™•์ธํ•  ์ˆ˜ ์žˆ๋‹ค. ๋ฐ์ดํ„ฐ๊ฐ€ ๋” ๋งŽ์€ ์ง‘ํ•ฉ์„ ๋จผ์ € ์•ก์„ธ์Šคํ•˜์—ฌ Hash Map์„ ์ƒ์„ฑํ•˜๋ ค๋ฉด ๊ทธ์— ๋”ฐ๋ฅธ ๋ถ€๋‹ด์ด ๋” ์ปค์งˆ ์ˆ˜๋„ ์žˆ๊ธฐ ๋•Œ๋ฌธ์— ํ–‰์ด ์ž‘์€ ํ…Œ์ด๋ธ”์„ Build Table๋กœ ์‚ผ๋Š”๋‹ค.

0๊ฐœ์˜ ๋Œ“๊ธ€