hash — std::hash

hash — std::hash

std::hash값을 해시(hash)하는 함수 객체를 제공하는 클래스 템플릿이에요. <functional> 헤더에 있어요.

std::hash<T>operator()T 값을 std::size_t 해시 값으로 변환해요. std::unordered_* 컨테이너의 기본 해시로 사용돼요.

출처: cppreference

본문

// <functional> 헤더
template< class T >
struct hash;

사용 예

#include <functional>
#include <unordered_map>
#include <string>

// 기본 hash 사용
std::unordered_map<std::string, int> m;   // 내부적으로 std::hash<string>
m["apple"] = 1;

// 직접 호출
std::hash<std::string> hasher;
std::size_t h = hasher("hello");

지원되는 타입

std::hash는 표준 기본 타입(int, double, 포인터), std::string, 스마트 포인터, std::thread::id, std::optional, std::variant, std::type_index 등 많은 타입에 특수화되어 있어요.

사용자 타입 확장

사용자 타입을 std::unordered_map의 키로 쓰려면 std::hash를 특수화할 수 있어요.

#include <functional>

struct Point { int x, y; bool operator==(const Point&) const = default; };

namespace std {
    template<> struct hash<Point> {
        std::size_t operator()(const Point& p) const noexcept {
            std::size_t h1 = std::hash<int>{}(p.x);
            std::size_t h2 = std::hash<int>{}(p.y);
            return h1 ^ (h2 << 1);   // 결합
        }
    };
}

// 이제 unordered_map<Point,...> 가능

특징

  • 같은 값은 항상 같은 해시 (같은 실행 내에서).
  • 다른 값은 가급적 다른 해시 (충돌 최소화).
  • noexcept.
std::unordered_set<Point> points;   // 특수화 후 사용 가능

std::hash는 해시 기반 컨테이너의 핵심이에요. 내장 타입은 바로 쓰고, 사용자 타입은 특수화해 해시 가능하게 만들 수 있어요.

더 알아보기 (Learn more)

cppreference