B-Tree index

ꡬ쑰 및 νŠΉμ„±

κ·Έλ¦Όκ³Ό 같이 인덱슀의 킀값은 λͺ¨λ‘ μ •λ ¬λ˜μ–΄ μžˆμ§€λ§Œ, μ‹€μ œ 데이터가 μ €μž₯된 데이터 νŒŒμΌμ—λŠ” μž„μ˜μ˜ μˆœμ„œλ‘œ μ €μž₯λ˜μ–΄ μžˆλ‹€. λ ˆμ½”λ“œκ°€ μ‚­μ œλ˜μ–΄ 빈 곡간이 생기면 κ·Έλ‹€μŒ INSERTλŠ” μ‚­μ œλœ 곡간을 μž¬ν™œμš©ν•˜λ„λ‘ DBMSκ°€ μ„€κ³„λ˜μ–΄ 있기 λ•Œλ¬Έμ— 항상 INSERT μˆœμ„œλ‘œ μ €μž₯λ˜μ§€ μ•ŠλŠ”λ‹€.

circle-info

λŒ€λΆ€λΆ„μ˜ RDMSλŠ” μž„μ˜μ˜ μˆœμ„œλ‘œ μ €μž₯λœλ‹€.

ν•˜μ§€λ§Œ InnoDB ν…Œμ΄λΈ”μ—μ„œ λ ˆμ½”λ“œλŠ” ν΄λŸ¬μŠ€ν„° λ˜μ–΄ λ””μŠ€ν¬μ— μ €μž₯λ˜λ―€λ‘œ 기본적으둜 PK μˆœμ„œλ‘œ μ •λ ¬λ˜μ–΄ μ €μž₯λœλ‹€. λ‹€λ₯Έ DBMSμ—μ„œλŠ” ν΄λŸ¬μŠ€ν„°λ§ κΈ°λŠ₯이 선택 μ‚¬ν•­μ΄μ§€λ§Œ, InnoDBμ—μ„œλŠ” λ””ν΄νŠΈλ‘œ ν΄λŸ¬μŠ€ν„°λ§ ν…Œμ΄λΈ”μ΄ μƒμ„±λœλ‹€.

ν΄λŸ¬μŠ€ν„°λ§μ΄λž€ λΉ„μŠ·ν•œ 값을 λͺ¨μ•„μ„œ μ €μž₯ν•˜λŠ” 방식을 μ˜λ―Έν•œλ‹€.

μΈλ±μŠ€λŠ” ν…Œμ΄λΈ”μ˜ PK 컬럼만 κ°€μ§€κ³  μžˆμœΌλ―€λ‘œ λ‚˜λ¨Έμ§€ μ»¬λŸΌμ„ 읽으렀면 μ‹€μ œ 데이터 νŒŒμΌμ—μ„œ ν•΄λ‹Ή λ ˆμ½”λ“œλ₯Ό μ°Ύμ•„μ•Ό ν•œλ‹€. 이λ₯Ό μœ„ν•΄ 인덱슀의 리프 λ…Έλ“œλŠ” μ‹€μ œ 데이터가 μ‘΄μž¬ν•˜λŠ” 데이터 νŒŒμΌμ—μ„œ λ ˆμ½”λ“œμ˜ μ£Όμ†Œλ₯Ό κ°–λŠ”λ‹€.

[MyISAM의 index table]

MyISAM μ—”μ§„μ˜ 경우, ν…Œμ΄λΈ” 생성 μ˜΅μ…˜μ— 따라 λ ˆμ½”λ“œκ°€ ν…Œμ΄λΈ”μ— INSERT 된 μˆœμ„œμ΄κ±°λ‚˜ 데이터 파일 λ‚΄μ˜ μœ„μΉ˜(Offset)이닀.

MyISAMκ³Ό InnoDB μŠ€ν† λ¦¬μ§€ μ—”μ§„μ˜ μΈλ±μŠ€μ—μ„œ κ°€μž₯ 큰 차이점은 세컨더리 인덱슀λ₯Ό 톡해 데이터 파일의 λ ˆμ½”λ“œλ₯Ό μ°Ύμ•„κ°€λŠ” 방법에 μžˆλ‹€. MyISAM은 세컨더리 μΈλ±μŠ€κ°€ 물리적인 μ£Όμ†Œλ₯Ό κ°€μ§€λŠ” 반면, InnoDBλŠ” PKλ₯Ό μ£Όμ†Œμ²˜λŸΌ μ‚¬μš©ν•˜κΈ° λ•Œλ¬Έμ— 논리적인 μ£Όμ†Œλ₯Ό κ°€μ§„λ‹€κ³  λ³Ό 수 μžˆλ‹€.

[InnoDB의 index table]

κ·Έλž˜μ„œ InnoDBμ—μ„œ 인덱슀λ₯Ό 톡해 λ ˆμ½”λ“œλ₯Ό μ‘°νšŒν•  λ•Œ, 데이터 νŒŒμΌμ„ λ°”λ‘œ μ°Ύμ•„κ°€μ§€ λͺ»ν•œλ‹€.

κ·Έλ¦Όκ³Ό 같이 μΈλ±μŠ€μ— μ €μž₯돼 μžˆλŠ” PK 값을 μ΄μš©ν•΄ PK 인덱슀λ₯Ό ν•œ 번 더 κ²€μƒ‰ν•œ ν›„, PK 인덱슀의 리프 νŽ˜μ΄μ§€μ— μ €μž₯돼 μžˆλŠ” λ ˆμ½”λ“œλ₯Ό μ½λŠ”λ‹€. 즉, InnoDB 엔진은 λͺ¨λ“  세컨더리 인덱슀 κ²€μƒ‰μ—μ„œ μ‹€μ œ λ ˆμ½”λ“œλ₯Ό 읽기 μœ„ν•΄μ„œλŠ” λ°˜λ“œμ‹œ PKλ₯Ό μ €μž₯ν•˜κ³  μžˆλŠ” B-Treeλ₯Ό λ‹€μ‹œ ν•œλ²ˆ 검색해야 ν•œλ‹€.

즉, 세컨더리 μΈλ±μŠ€κ°€ PK의 값을 μ €μž₯ν•˜κ³  μžˆλ‹€. (이쀑 인덱슀 탐색 방식)

  1. 세컨더리 μΈλ±μŠ€μ—μ„œ 쑰건에 λ§žλŠ” PKλ₯Ό μ°ΎλŠ”λ‹€.

  2. 찾은 PK둜 ν΄λŸ¬μŠ€ν„°λ“œ 인덱슀λ₯Ό κ²€μƒ‰ν•˜μ—¬ μ‹€μ œ 데이터λ₯Ό μ‘°νšŒν•œλ‹€.

λ§Œμ•½, email 컬럼이 인덱슀둜 μ„€μ •λ˜μ–΄ 있으면

  1. λ¨Όμ € idx_email μΈλ±μŠ€μ—μ„œ where 쑰건에 ν•΄λ‹Ήν•˜λŠ” id(PK)λ₯Ό μ°ΎλŠ”λ‹€.

  2. 찾은 id(PK) κ°’μœΌλ‘œ 프라이머리 인덱슀λ₯Ό 톡해 μ‹€μ œ 데이터λ₯Ό μ‘°νšŒν•œλ‹€.

MyISAM 인덱슀 ꡬ쑰와 비ꡐ해 보면, 이 κ΅¬μ‘°λŠ” μ„±λŠ₯이 λ–¨μ–΄μ§ˆ κ²ƒμ²˜λŸΌ λ³΄μ΄μ§€λ§Œ 각각 μž₯단점을 κ°€μ§€κ³  μžˆλ‹€.

  • MyISAM ν…Œμ΄λΈ”μ— μ €μž₯λ˜λŠ” λ ˆμ½”λ“œλŠ” λͺ¨λ‘ ROWIDλΌλŠ” 물리적인 μ£Όμ†Œ 값을 κ°–λŠ”λ‹€.

두 μ—”μ§„μ˜ κ°€μž₯ 큰 차이점은 세컨더리 인덱슀λ₯Ό 톡해 데이터 파일의 λ ˆμ½”λ“œλ₯Ό μ°Ύμ•„κ°„λ‹€λŠ” 것이닀.

인덱슀 ν‚€ μΆ”κ°€

ν…Œμ΄λΈ”μ˜ λ ˆμ½”λ“œλ₯Ό λ³€κ²½ν•˜λŠ” 경우, 인덱슀 ν‚€ μΆ”κ°€λ‚˜ μ‚­μ œ μž‘μ—…μ΄ λ°œμƒν•œλ‹€.

인덱슀 ν‚€ μΆ”κ°€/μ‚­μ œκ°€ μ–΄λ–»κ²Œ μ²˜λ¦¬λ˜λŠ”μ§€ μ•ˆλ‹€λ©΄ 쿼리 μ„±λŠ₯을 μ˜ˆμΈ‘ν•˜κ³  μ£Όμ˜ν•΄μ•Ό ν•  점도 μ•Œ 수 μžˆμ„ 것이닀.

μƒˆλ‘œμš΄ ν‚€ 값이 B-Tree에 μ €μž₯될 λ•Œ ν…Œμ΄λΈ”μ˜ μŠ€ν† λ¦¬μ§€ 엔진에 λ”°λΌμ„œ μƒˆλ‘œμš΄ ν‚€ 값이 μ¦‰μ‹œ μΈλ±μŠ€μ— μ €μž₯될 수 있고 κ·Έλ ‡μ§€ μ•Šμ„ 수 μžˆλ‹€.

μ €μž₯ μœ„μΉ˜κ°€ κ²°μ •λ˜λ©΄ λ ˆμ½”λ“œμ˜ ν‚€ κ°’κ³Ό λŒ€μƒ λ ˆμ½”λ“œμ˜ μ£Όμ†Œ 정보λ₯Ό 리프 λ…Έλ“œμ— μ €μž₯ν•œλ‹€.

리프 λ…Έλ“œκ°€ 가득 μ°¨μ„œ μ €μž₯ν•  수 μ—†λ‹€λ©΄ 리프 λ…Έλ“œμ—μ„œ 뢄리(μŠ€ν”Œλ¦Ώ)이 λ°œμƒν•˜λŠ”λ°, μ΄λ ‡κ²Œ μž¬μ‘°μ •ν•˜λŠ” 과정은 μƒμœ„ 브랜치 λ…Έλ“œκΉŒμ§€ 처리 λ²”μœ„κ°€ λ„“μ–΄μ§€κΈ° λ•Œλ¬Έμ— B-TreeλŠ” μƒλŒ€μ μœΌλ‘œ μ“°κΈ° μž‘μ—…μ— λΉ„μš©μ΄ 많이 λ“ λ‹€.

μ€‘μš”ν•œ 것은 λΉ„μš©μ˜ λŒ€λΆ€λΆ„μ΄ λ©”λͺ¨λ¦¬μ™€ CPUμ—μ„œ μ²˜λ¦¬ν•˜λŠ” μ‹œκ°„μ΄ μ•„λ‹ˆλΌ λ””μŠ€ν¬λ‘œλΆ€ν„° 인덱슀 νŽ˜μ΄μ§€λ₯Ό 읽고 μ“°κΈ°λ₯Ό ν•΄μ•Ό ν•΄μ„œ κ±Έλ¦¬λŠ” μ‹œκ°„μΈ disk I/O이닀.

B-Tree μ“°κΈ° μž‘μ—…μ‹œ λ°œμƒν•˜λŠ” λ””μŠ€ν¬ I/OλŠ” μ•„λž˜μ™€ 같을 수 μžˆλ‹€.

  • μƒˆλ‘œμš΄ ν‚€ μ‚½μž…μ‹œ 리프 λ…Έλ“œ 읽기

  • 리프 λ…Έλ“œκ°€ 가득 μ°¨μ„œ μŠ€ν”Œλ¦Ώ μž‘μ—…

  • λΆ„ν• λœ λ…Έλ“œλ₯Ό λ””μŠ€ν¬μ— write

  • μƒμœ„ 브랜치 λ…Έλ“œ κ°±μ‹ 

μ΄λŸ¬ν•œ 이유둜 B-Tree μΈλ±μŠ€λŠ” 읽기 μž‘μ—…μ— μ΅œμ ν™”λ˜μ–΄ 있으며 μ“°κΈ° μž‘μ—…μ€ μƒλŒ€μ μœΌλ‘œ λΉ„μš©μ΄ 많이 λ°œμƒν•œλ‹€.

λ”°λΌμ„œ λΆˆν•„μš”ν•œ 인덱슀λ₯Ό λ§Œλ“€λ©΄ μ“°κΈ° μ„±λŠ₯이 크게 μ €ν•˜λ  수 μžˆμ–΄, 인덱슀 섀계 μ‹œ μ΄λŸ¬ν•œ 뢀뢄듀을 κ³ λ €ν•΄μ•Ό ν•œλ‹€.

인덱슀 ν‚€ μ‚­μ œ

ν‚€ μ‚­μ œλŠ” κ°„λ‹¨ν•˜λ‹€. ν‚€ 값이 μ €μž₯된 리프 λ…Έλ“œλ₯Ό μ°Ύμ•„μ„œ 마크만 ν•˜λ©΄ 끝이닀.

μ‚­μ œ λ§ˆν‚Ήλœ 인덱슀 ν‚€ 곡간은 κ·ΈλŒ€λ‘œ λ‘κ±°λ‚˜ μž¬ν™œμš©ν•  수 μžˆλ‹€. λ§ˆν‚Ή μž‘μ—… λ˜ν•œ disk writeκ°€ ν•„μš”ν•΄μ„œ 이 λ˜ν•œ disk I/Oκ°€ ν•„μš”ν•œ μž‘μ—…μ΄λ‹€.

인덱슀 ν‚€ λ³€κ²½

인덱슀의 ν‚€ 값은 값에 따라 리프 λ…Έλ“œμ˜ μœ„μΉ˜κ°€ κ²°μ •λœλ‹€. κ·Έλž˜μ„œ ν‚€ 값이 λ³€κ²½λ˜λŠ” 경우 λ‹¨μˆœνžˆ ν‚€ κ°’λ§Œ λ³€κ²½ν•˜λŠ” 것은 λΆˆκ°€λŠ₯ν•˜λ‹€.

B-Treeμ—μ„œ ν‚€ κ°’ 변경은 λ¨Όμ € ν‚€λ₯Ό μ‚­μ œν•˜κ³  λ‹€μ‹œ μƒˆλ‘œμš΄ ν‚€ 값을 μΆ”κ°€ν•˜λŠ” λ°©μ‹μœΌλ‘œ μ²˜λ¦¬λœλ‹€. μ•žμ—μ„œ μ„€λͺ…ν•œ μΆ”κ°€/μ‚­μ œ μž‘μ—…μ΄ μ ˆμ°¨λŒ€λ‘œ 처리되기 λ•Œλ¬Έμ— 이 μ—­μ‹œλ„ disk I/Oκ°€ λ°œμƒν•œλ‹€.

인덱슀 ν‚€ 검색

B-Treeμ—μ„œ μΆ”κ°€/μ‚­μ œ/λ³€κ²½κ³Ό 같은 무거운 λΉ„μš©μ„ κ°λ‹Ήν•˜λ©΄μ„œ 인덱슀λ₯Ό κ΅¬μΆ•ν•˜λŠ” μ΄μœ λŠ” λ°”λ‘œ λΉ λ₯Έ 검색이닀.

루트 λ…Έλ“œ β†’ 브랜치 λ…Έλ“œ β†’ 리프 λ…Έλ“œκΉŒμ§€ μ΄λ™ν•˜λ©΄μ„œ 비ꡐ μž‘μ—…μ„ μˆ˜ν–‰ν•˜λŠ”λ°, 이 과정을 β€œνŠΈλ¦¬ 탐색” 이라고 ν•œλ‹€.

트리 탐색은 selectμ—μ„œλ§Œ μ‚¬μš©ν•˜λŠ” 것이 μ•„λ‹ˆλΌ update, deleteλ₯Ό μ²˜λ¦¬ν•˜κΈ° μœ„ν•΄ ν•΄λ‹Ή λ ˆμ½”λ“œλ₯Ό λ¨Όμ € 검색해야 ν•˜λŠ” κ²½μš°μ—λ„ μ‚¬μš©λœλ‹€.

인덱슀 검색은 ν‚€ κ°’μ˜ μ•žλΆ€λΆ„μ΄ μΌμΉ˜ν•˜λŠ” κ²½μš°μ— μ‚¬μš©ν•  수 μžˆλ‹€. λΆ€λ“±ν˜Έ(<, >) 비ꡐ μ‘°κ±΄μ—μ„œλ„ ν™œμš©ν•  수 μžˆμ§€λ§Œ, ν‚€ κ°’μ˜ λ’·λΆ€λΆ„λ§Œμ„ κ²€μƒ‰ν•˜λŠ” μš©λ„λ‘œλŠ” μ‚¬μš©ν•  수 μ—†λ‹€.

인덱슀 κ²€μƒ‰μ—μ„œ μ€‘μš”ν•œ 것은 ν‚€ κ°’μ˜ λ³€ν˜•, 즉 μ‘°νšŒν•˜λ €λŠ” 데이터가 λ³€ν˜•λœλ‹€λ©΄ λΉ λ₯Έ 검색 κΈ°λŠ₯을 μ‚¬μš©ν•  수 μ—†λ‹€. κ·Έ μ΄μœ λŠ” ν•¨μˆ˜λ‚˜ 연산을 μˆ˜ν–‰ν•œ κ²°κ³ΌλŠ” μΈλ±μŠ€μ— μ‘΄μž¬ν•˜λŠ” 값이 μ•„λ‹ˆκΈ° λ•Œλ¬Έμ΄λ‹€. κ·Έλž˜μ„œ 인덱슀λ₯Ό 타지 μ•ŠλŠ” λŒ€ν‘œμ μΈ κ²½μš°μ—λŠ” ν•¨μˆ˜ λ˜λŠ” μ—°μ‚°μžλ₯Ό μ‚¬μš©ν•˜λŠ” κ²½μš°κ°€ ν¬ν•¨λ˜λŠ” 것이닀.

Q&A

  1. ν•΄μ‹œ 인덱슀 λŒ€μ‹  B-Treeλ₯Ό μ‚¬μš©ν•˜λŠ” 이유

  • λ²”μœ„ 검색 지원

    • B-TreeλŠ” 데이터λ₯Ό μ •λ ¬λœ μƒνƒœλ‘œ μœ μ§€ν•˜λ―€λ‘œ λΆ€λ“±ν˜Έ μ—°μ‚°(<, >, between λ“±)을 효율적으둜 μ²˜λ¦¬ν•  수 μžˆμ§€λ§Œ, ν•΄μ‹œ μΈλ±μŠ€λŠ” 동등 λΉ„κ΅μ—λ§Œ μ΅œμ ν™” λ˜μ–΄ μžˆλ‹€. λ²”μœ„ κ²€μƒ‰μ΄λ‚˜ μ •λ ¬λ˜μ§€ μ•Šμ€ κ²°κ³Όλ₯Ό κ°€μ Έμ˜€κΈ° μœ„ν•΄μ„œλŠ” λ§Žμ€ λ””μŠ€ν¬ I/Oλ₯Ό μœ λ°œν•  수 μžˆλ‹€.

  • μ •λ ¬κ³Ό 순차 μ ‘κ·Ό

    • ν•΄μ‹œλŠ” μ •λ ¬ μˆœμ„œκ°€ 보μž₯λ˜μ§€ μ•Šμ•„ order by μ‹œ μΆ”κ°€ μ •λ ¬ μž‘μ—…μ΄ ν•„μš”ν•  수 μžˆλ‹€.

    • B-TreeλŠ” 이미 데이터가 μ •λ ¬λ˜μ–΄ μžˆμ–΄μ„œ order/group by 등이 νš¨μœ¨μ μ΄λ‹€.

  • λΆ€λΆ„ 검색(Prefix Search)

    • ν•΄μ‹œλŠ” μ™„μ „ν•œ ν‚€ 값이 μ‘΄μž¬ν•΄μ•Όλ§Œ 검색이 κ°€λŠ₯ν•˜λ‹€. (LIKE 'Kim%'같은 검색이 λΉ„νš¨μœ¨μ )

    • B-TreeλŠ” ν‚€μ˜ μΌλΆ€λΆ„λ§ŒμœΌλ‘œ 검색이 κ°€λŠ₯ν•˜λ‹€. (LIKE 'Kim%'같은 νŒ¨ν„΄ 검색 효율적)

  • λ””μŠ€ν¬ I/O

    • ν•΄μ‹œλŠ” ν‚€λ§ˆλ‹€ λžœλ€ν•œ μœ„μΉ˜ μ ‘κ·ΌμœΌλ‘œ λ””μŠ€ν¬ I/O 많이 λ°œμƒ

    • B-TreeλŠ” ν•˜λ‚˜μ˜ λ…Έλ“œμ— μ—¬λŸ¬ ν‚€λ₯Ό μ €μž₯ν•  수 μžˆλŠ” ꡬ쑰적 νŠΉμ„±μœΌλ‘œ I/O νš¨μœ¨μ„±μ„ λ†’μ΄λŠ”λ° κΈ°μ—¬

Last updated