자료구조 정복하기 3

정지인·2025년 6월 21일

📌 Hashing (해싱)

✅ 개념 요약

  • Hashing은 데이터를 저장하고 조회하는 데 사용되는 고속 탐색 기법으로, 배열 기반 자료구조와 **해시 함수(hash function)**를 이용하여 구현됨.
  • 일반적으로 해시는 **키(key)**를 기반으로 한 값을 특정한 위치에 빠르게 저장하거나 검색함.
  • 정렬이 필요 없는 탐색 방식이며, 시간 복잡도는 평균적으로 **O(1)**에 가까움.

🔐 해시 함수 (Hash Function)

  • 입력값(key)을 고정된 크기의 배열 인덱스로 매핑하는 함수
  • 동일한 입력값은 항상 동일한 해시값을 반환해야 함

특징

  • 결정성: 동일한 입력에 대해 항상 동일한 해시값 반환
  • 해시값은 일반적으로 배열의 인덱스로 사용됨
int hash(int key) {
    return key % TABLE_SIZE;
}

⚠️ 충돌(Collision)과 처리 방법

  • 서로 다른 키가 동일한 해시 인덱스를 가질 경우 발생
  • 이를 해결하기 위해 다양한 충돌 해결 전략이 사용됨

1. 체이닝 (Chaining)

  • 각 배열 인덱스가 연결 리스트를 가지며 충돌된 키들을 리스트에 추가
  • 공간 낭비는 줄지만, 평균 탐색 시간은 O(n/k)로 느려질 수 있음

2. 선형 탐사 (Linear Probing)

  • 충돌 발생 시, 다음 인덱스로 이동하여 빈 자리를 찾는 방법
  • 클러스터링 문제 발생 가능
int hash(int key) {
    int index = key % TABLE_SIZE;
    while (table[index] != EMPTY) {
        index = (index + 1) % TABLE_SIZE;
    }
    return index;
}

3. 이차 탐사 (Quadratic Probing)

  • 선형이 아닌 제곱 간격으로 이동: index + i^2
  • 클러스터링을 완화할 수 있음

4. 더블 해싱 (Double Hashing)

  • 두 개의 해시 함수를 사용하여 충돌 시 보조 해시 함수로 재계산
  • 가장 효과적인 오픈 어드레싱 방식 중 하나

🔁 리사이징 (Resizing)

  • 해시 테이블의 크기를 동적으로 늘리는 방법
  • 보통 **로드 팩터(load factor)**가 일정 비율 이상이 되면 리사이징 수행
  • 리사이징 시 모든 원소를 새로운 해시 테이블로 재해싱(rehash) 해야 함

⏱ 시간 복잡도

연산평균최악
검색(Search)O(1)O(n)
삽입(Insert)O(1)O(n)
삭제(Delete)O(1)O(n)
  • 충돌이 없다면 O(1), 충돌이 많아질수록 O(n)에 가까워짐

🟩 장점

  • 매우 빠른 검색/삽입/삭제 연산 가능 (평균 O(1))
  • 정렬이 필요 없는 환경에서 효율적

🟥 단점

  • 메모리 사용량 증가 가능
  • 해시 함수 설계가 성능에 결정적
  • 충돌 처리 알고리즘이 필요

✅ 활용 예시

  • 데이터베이스 인덱싱
  • 캐시 시스템 (예: LRU Cache)
  • 중복 검사 (중복 문자 탐지 등)
  • 사전(Dictionary), 집합(Set) 구현

✅ 핵심 요약

Hashing은 **규칙성 있는 키 변환 함수(hash function)**와 충돌 대응 전략을 통해 데이터를 빠르고 효율적으로 다루는 자료구조이다.

profile
멋쟁이사자 13기 백엔드

0개의 댓글