Foundry
안정 해시 설계
중급
핵심

담당 지점을 찾는 방법

정렬해 두고 반씩 좁힌다

앞 단계에서 링 항목이 15,000개가 됐습니다. 이제 조회마다 그 안에서 담당을 찾아야 합니다. 예산은 0.1ms 이고 이 계산은 초당 50만 번 실행됩니다.

정렬해 두고 반씩 좁힌다

링을 정렬된 목록으로 두고 반씩 좁혀 담당 지점을 찾는다. 양 끝은 같은 점이다 링을 펼쳐 정렬해 둔다. 눈금은 서버 지점 이 키 첫 지점이 담당 0 끝 = 처음 정렬돼 있으므로 반씩 좁혀 찾는다 15,000개면 14단계. 0.1ms 안에 끝난다 마지막 지점을 지난 키는 처음 지점으로 감싼다

링을 펼쳐 위치 순으로 정렬한 목록으로 둡니다. 그러면 "이 키의 해시 값보다 크거나 같은 첫 지점" 을 반씩 좁혀 찾을 수 있습니다.

15,000개를 반씩 좁히면 14단계
비교 14번이면 0.1ms 예산 안에 넉넉하다

담당을 찾는 일이 목록을 처음부터 훑는 것이 되면 15,000번 비교가 되고, 초당 50만 조회면 초당 75억 번의 비교가 됩니다. 정렬 상태를 유지하는 것이 이 설계의 전제입니다.

감싸기를 빼먹지 않는다

링의 양 끝은 같은 점입니다. 해시 값이 마지막 지점보다 큰 키는 시계 방향으로 돌아 처음 지점을 만납니다.

이 처리를 빼먹으면 그 구간의 키에서 담당을 못 찾습니다. 구현에서 가장 흔한 실수이고, 평소에는 드러나지 않다가 키의 일부에서만 실패하므로 원인을 찾기 어렵습니다.

어디서 계산하나

계산 자체는 값싸지만 링을 누가 들고 있느냐가 갈립니다.

위치왕복대가
클라이언트가 계산없다모든 클라이언트가 링을 들고 있어야 한다
앞단 프록시가 계산한 번 늘어난다링은 한 곳만 갱신하면 된다
아무 서버에 보내고 넘기기내부에서 한 번구현이 단순하다. 절반이 두 번 이동한다

예산 0.1ms 는 왕복을 허용하지 않으므로 이 요구사항에서는 클라이언트가 계산합니다. 그 대가로 링을 모두에게 나눠 주는 일이 생기고, 다음 단계가 그 이야기입니다.

해시 함수는 빠른 것을 고른다

이 해시는 보안용이 아니라 분배용입니다. 초당 50만 번 실행되므로 속도가 중요하고, 필요한 성질은 값이 고르게 흩어지는 것뿐입니다.

성질필요한가
고른 분포필요하다. 편차가 곧 부하 편차다
빠른 계산필요하다. 요청 경로에 있다
역산이 어려움필요 없다. 비밀을 지키는 용도가 아니다

암호용 해시는 역산을 어렵게 만드는 값을 치르므로 느립니다. 그 값을 여기서는 낼 이유가 없습니다.

키와 서버 위치에 같은 함수를 써야 합니다. 다른 함수를 쓰면 두 값이 같은 공간에 놓이지 않아 담당 규칙 자체가 성립하지 않습니다.

면접에서 이렇게 나옵니다

Q.링에서 담당 지점을 어떻게 찾나요

위치 순으로 정렬해 두고 반씩 좁혀 찾습니다. 키의 해시 값보다 크거나 같은 첫 지점이 담당입니다.

링 항목 15,000개를 반씩 좁히면 14단계
비교 14번이면 0.1ms 예산 안에 넉넉하다

처음부터 훑으면 15,000번 비교가 되고, 조회 초당 50만 이면 초당 75억 번의 비교가 됩니다. 정렬 상태를 유지하는 것이 전제입니다.

그리고 감싸기를 처리해야 합니다. 링의 양 끝은 같은 점이므로 마지막 지점보다 큰 해시 값은 처음 지점으로 돌아갑니다.

흔한 실수: 감싸기를 빼먹는 것. 평소에는 드러나지 않다가 마지막 지점 뒤 구간의 키에서만 담당을 못 찾습니다. 일부 키에서만 실패하므로 원인을 찾기 어렵습니다.

Q.담당 계산을 어디에서 하시겠습니까

클라이언트에서 합니다. 예산 0.1ms 가 왕복을 허용하지 않습니다.

위치왕복대가
클라이언트없다모든 클라이언트가 링을 들고 있어야 한다
앞단 프록시한 번 늘어난다링은 한 곳만 갱신하면 된다
아무 서버에 보내고 넘기기내부에서 한 번구현이 단순하다

프록시 방식은 링 관리가 훨씬 쉬워서 실무에서 많이 쓰입니다. 지연 예산이 넉넉하다면 그쪽이 운영 부담이 작습니다.

흔한 실수: 위치를 고르면서 그 선택이 만드는 새 문제를 말하지 않는 것. 클라이언트 계산을 고르면 링을 수천 개 인스턴스에 나눠 주고 같게 유지하는 일이 따라옵니다. 그것을 함께 말해야 설계가 이어집니다.

Q.어떤 해시 함수를 쓰시겠습니까

빠르고 분포가 고른 비암호용 해시를 씁니다.

성질필요한가
고른 분포필요하다. 편차가 곧 부하 편차다
빠른 계산필요하다. 요청 경로에 있다
역산이 어려움필요 없다

이 해시는 비밀을 지키는 용도가 아니라 분배용입니다. 암호용 해시는 역산을 어렵게 만드는 값을 치르므로 느리고, 그 값을 여기서 낼 이유가 없습니다.

그리고 키와 서버 위치에 같은 함수를 써야 합니다. 다르면 두 값이 같은 공간에 놓이지 않아 담당 규칙이 성립하지 않습니다.

흔한 실수: 해시 값의 음수 처리를 놓치는 것. 부호 있는 정수를 반환하는 함수를 쓰면 음수가 나오고, 그대로 위치로 쓰면 링 범위를 벗어납니다. 이런 실수는 일부 키에서만 드러나 찾기 어렵습니다.

Q.링 항목이 더 늘어나면 찾기가 느려지지 않나요

반씩 좁히므로 항목이 두 배가 될 때 한 단계만 늘어납니다.

15,000개 = 14단계
30,000개 = 15단계
100만 개 = 20단계

그래서 탐색 비용은 지점 수를 정하는 데 큰 제약이 아닙니다. 실제 제약은 다른 쪽입니다. 링이 커지면 구성이 바뀔 때 모두에게 알려야 하는 양이 커집니다.

늘어나는 것영향
탐색 단계거의 안 늘어난다
링 전달 크기항목 수에 비례해 늘어난다

흔한 실수: 탐색 비용을 근거로 지점 수를 아끼는 것. 실제로 아껴야 하는 이유는 갱신 전파 쪽이고, 그 판단은 구성 변경 빈도와 클라이언트 수에서 나옵니다.

먼저 스스로 답해보고 아래 답변과 견줘보세요. 막히는 부분은 문제로 확인할 수 있어요.

읽었으면 문제로 확인해보세요

안정 해시 설계 문제를 풀면 틀린 문제가 자동으로 노트에 쌓입니다. 가입 없이 5문제를 먼저 풀어볼 수도 있어요.