개요
벤치마크는 “지금 이 코드가 이 하드웨어에서 몇 초 걸리는가"라는 사실은 알려주지만, 그 숫자가 이미 물리적 한계에 가까운 좋은 결과인지 아니면 어딘가 구조적 결함이 숨어 있는 나쁜 결과인지는 알려주지 않는다. 10초짜리 벤치마크 결과를 보고 “이 작업의 물리적 한계가 10초"인지 “물리적 한계는 10밀리초인데 뭔가가 1000배 느리게 만들고 있는지"를 벤치마크 수치 하나만으로는 구별할 수 없다.
Turbopuffer 공동창업자 겸 CEO Simon Eskildsen(Shopify에서 2013–2021년 인프라를 담당했고, 이후 2023년 Turbopuffer를 공동창업)은 이 문제를 “napkin math”(냅킨 계산)라는 습관으로 풀어왔다고 The Pragmatic Engineer 인터뷰에서 설명했다(The Pragmatic Engineer, 2026-07-21). 핵심은 벤치마크를 돌려보기 전에 메모리 대역폭·디스크 접근 지연 같은 하드웨어 1차 원리(first principles)로 “이 작업이 물리적으로 얼마나 빨라야 하는가"를 암산 수준으로 먼저 추정해두는 것이다. 이 글은 그 방법론이 실제로 어떻게 병목을 찾아냈는지 두 가지 구체적 사례로 보고, 누구나 바로 쓸 수 있는 기준 수치표와 적용 판단 기준을 정리한다.
Napkin Math란 무엇인가
Napkin math는 정밀한 벤치마크나 프로파일링 없이, 하드웨어의 근본적 한계치를 암산 수준의 빠른 계산으로 먼저 추정해보는 습관이다. Eskildsen은 인터뷰에서 DRAM 메모리 대역폭, 네트워크 왕복 시간, 기가바이트당 저장 비용처럼 계산의 기준점이 되는 핵심 수치 약 50개를 스크립트로 관리되는 표 형태로 정리해두고 언제든 꺼내 쓴다고 밝혔다. 이 상수들은 특정 프로젝트 전용이 아니라, “이 작업이 물리적으로 얼마나 빨라야 하는가"라는 질문에 즉답하기 위한 재사용 가능한 기준값 집합이다.
이 방법론은 2019년부터 Eskildsen이 직접 유지·관리해온 오픈소스 저장소 napkin-math로 공개돼 있다. 이 저장소는 메모리 순차/랜덤 접근, 같은 리전·리전 간·글로벌 네트워크 왕복, SSD·HDD·블롭 스토리지 접근, 해싱·정렬·압축 같은 연산, CPU·메모리·스토리지·네트워킹 비용까지 성능 추정에 필요한 기준 수치를 모아두고, 실제 클라우드 인스턴스에서 주기적으로 재측정해 값을 검증한다(가장 최근 갱신은 2026년 3월 8일, GCP c4-standard-48-lssd 인스턴스 기준이다, GitHub: sirupsen/napkin-math).
어떻게 계산하는가 — 두 가지 실전 사례
사례 1: 검색 쿼리가 왜 10초나 걸리는가
인터뷰에서 Eskildsen이 든 첫 번째 사례는 검색 쿼리 성능 분석이다. 검색어 각각이 매칭되는 문서 수와 그 목록의 크기(메가바이트 단위)를 구하고, 여러 코어를 병렬로 쓸 때의 합산 DRAM 대역폭(인터뷰에서 든 기준값은 약 100GB/초)을 기준으로 그 목록들을 메모리에서 교집합 연산하는 데 걸리는 시간을 계산하면 이론상 10밀리초 안팎이어야 한다는 결론이 나온다. 그런데 실제 벤치마크는 10초가 걸렸다 — 세 자릿수 배율의 격차다.
이 격차 자체가 문제의 소재를 알려준다. 단일 머신의 순수 연산 속도가 병목이 아니라, 여러 노드를 오가는 분산 쿼리 처리 구조(통신·조정 오버헤드) 쪽에 병목이 있다는 뜻이다. 냅킨 계산이 정확한 답을 준 게 아니라, “왜 1000배나 차이가 나는가"라는 질문을 만들어냈고 그 질문이 실제 병목의 위치(단일 노드가 아니라 분산 구조)를 가리켰다.
사례 2: MySQL은 왜 이론치보다 5배 빠른가
두 번째 사례는 반대 방향의 격차다. 트랜잭션마다 디스크에 안전하게 쓰기 위한 fsync 호출이 필요하다고 가정하면, 일반적인 fsync 지연시간 기준으로 초당 약 1,000건이 이론적 상한이라는 계산이 나온다. 그런데 실측 처리량은 초당 약 5,300건, 이론치의 5배였다.
실측이 이론 상한을 초과하는 이 반대 방향의 격차는 “가정 자체가 틀렸다"는 신호다. 실제로는 MySQL이 여러 트랜잭션의 커밋을 하나의 fsync 호출로 묶어 처리하는 그룹 커밋(group commit) 메커니즘을 쓰고 있었기 때문이다. 냅킨 계산이 “트랜잭션 하나당 fsync 한 번"이라는 순진한 가정으로는 설명되지 않는 처리량을 만나자, 그 자체가 시스템이 뭔가 다른 메커니즘을 쓰고 있다는 단서가 됐다.
두 사례 모두 냅킨 계산 자체가 정답을 주는 게 아니라, “이론치와 실측치가 왜 이만큼 어긋나는가"라는 질문을 만들어내고 그 질문이 실제 시스템 구조를 드러내는 단서로 쓰였다는 공통점이 있다. 격차의 방향도 진단 정보다 — 실측이 이론보다 훨씬 느리면 구조적 병목(사례 1)을, 실측이 이론보다 빠르면 계산에 포함하지 않은 최적화 메커니즘의 존재(사례 2)를 가리킨다.
기준이 되는 하드웨어 수치표
냅킨 계산을 실전에서 바로 쓰려면 암기할 기준값이 있어야 한다. 아래는 napkin-math 저장소가 공개하는 수치 중 자릿수 감각을 잡는 데 핵심적인 항목들을 정리한 것이다. 정확한 소수점 값이 아니라 자릿수(order of magnitude) 단위로 기억해두는 것이 이 표의 목적이다.
| 구분 | 항목 | 대략적인 자릿수 |
|---|---|---|
| 메모리 | 순차 접근 대역폭(단일 스레드) | 수십GB/초 |
| 메모리 | 순차 접근 대역폭(여러 코어 합산) | 수백GB/초대(100–200GB/초) |
| 메모리 | 랜덤 접근 지연 | 수십–수백ns |
| 네트워크 | 같은 리전 왕복(RTT) | 0.25ms 안팎 |
| 네트워크 | 리전 간 왕복(RTT) | 수십–수백ms |
| 디스크 | SSD 랜덤 읽기 지연 | 수십–수백µs |
| 디스크 | fsync 1회 지연(회전 디스크 기준) | 약 1ms |
| 디스크 | HDD 순차 읽기 대역폭 | 수백MB/초 |
| 스토리지 | 블롭 스토리지(S3 등) 왕복 | 수십–수백ms |
출처: GitHub: sirupsen/napkin-math — 2026-03-08 GCP c4-standard-48-lssd 인스턴스 재측정 기준(단일 스레드 대역폭과 멀티스레드 합산 대역폭을 별도 항목으로 측정). 정확한 수치는 클라우드 벤더·인스턴스 타입·시점에 따라 달라지므로, 이 표는 “어느 자릿수를 먼저 의심해야 하는가"를 잡는 용도로만 쓴다.
이 표를 손에 쥐고 있으면 “이 작업은 네트워크 5번 왕복 + 메모리 스캔 1번이니 대략 몇 ms가 나와야 한다"는 식의 계산을 실측 전에 먼저 해볼 수 있다. 실측치가 이 추정과 자릿수 단위로 어긋나면, 그 어긋남의 방향이 다음 조사 방향을 알려준다.
벤치마크 우선 접근, 프로파일러 우선 접근과 비교하면
병목을 찾는 세 가지 접근을 비교하면 냅킨 계산이 채우는 빈틈이 분명해진다.
| 접근 | 얻는 것 | 한계 |
|---|---|---|
| 벤치마크 먼저 실행 | 실제 환경에서 정확한 실측 수치 | 그 수치가 좋은지 나쁜지 판단할 기준선이 없음 |
| 프로파일러로 코드 레벨 분석 | 실행 중 시간이 어디서 쓰이는지 직접 추적 | 분산 시스템의 노드 간 오버헤드나 아키텍처 수준 병목은 단일 프로세스 프로파일링으로 잘 안 보임 |
| 냅킨 계산(하드웨어 1차 원리) | 실측 전에 세워둔 기준선, 격차의 방향으로 병목 유형을 좁힘 | 자릿수 단위의 어림값이라 정밀한 용량 산정의 최종 근거로는 부족함 |
세 접근은 서로 대체재가 아니라 보완재에 가깝다. 냅킨 계산으로 “이 정도 격차면 분산 구조를 봐야 한다” 또는 “이 정도면 이미 하드웨어 한계 근처다"라고 먼저 방향을 좁혀두면, 그다음 벤치마크와 프로파일러를 어디에 집중할지가 정해진다.
실전에서 검증된 사례 — Shopify의 durability 원칙과 toxiproxy
같은 인터뷰에서 Eskildsen은 Shopify에서 인프라를 오래 담당하며 얻은 교훈으로 소프트웨어를 “오래 지속되도록”(durable) 만드는 것을 꼽았다. 몇 주 안에 만든 단순한 해법이 대규모 설계 검토를 거친 정교한 해법보다 오히려 더 오래 살아남는 경우가 많았다는 관찰이다.
이 시기 Shopify에서 나온 오픈소스 결과물 중 하나가 toxiproxy다. Toxiproxy는 애플리케이션과 데이터베이스(또는 다른 의존 서비스) 사이에 위치하는 TCP 프록시로, API 호출로 특정 연결을 끊거나 느리게 만들어 부분 장애 상황에서 시스템 전체의 복원력을 테스트할 수 있게 하는 카오스 엔지니어링 도구다. Shopify는 2014년 10월부터 모든 개발·테스트 환경에서 toxiproxy를 써왔고, 목적은 “단일 장애점(single point of failure)이 없다"는 것을 실제 테스트로 증명하는 데 있다(GitHub: Shopify/toxiproxy). 결정론적 지연을 만들 수 있는 기존 도구가 마땅치 않아 직접 만들었다는 것이 Eskildsen의 설명이다.
냅킨 계산(이론 상한을 먼저 계산)과 durability 원칙(오래가는 단순한 설계), toxiproxy(장애를 실제로 주입해 검증)는 같은 태도의 세 가지 표현으로 읽을 수 있다. 셋 다 “그럴듯해 보이는 것"과 “실제로 검증된 것"을 구분하려는 접근이라는 공통점이 있다. 다만 이 연결은 인터뷰가 명시적으로 서술한 내용이 아니라 사후적 해석이므로, 사실 주장이 아니라 하나의 관점으로 읽는 편이 맞다.
언제 쓰고 언제 한계가 있는가
냅킨 계산은 시스템 설계 초기 단계에서 여러 설계안 중 하드웨어 한계상 애초에 불가능한 안을 먼저 걸러낼 때, 그리고 벤치마크 결과가 나온 뒤 그 결과가 병목의 신호인지 정상인지 빠르게 판단할 기준선이 필요할 때 특히 유용하다. 반대로 이미 병목의 위치가 명확하거나, 문제가 하드웨어 물리적 한계가 아니라 로직 오류·설정 실수처럼 순수 소프트웨어적 원인일 때는 냅킨 계산보다 직접적인 디버깅이 더 빠른 답을 준다. 자릿수 단위의 어림값이므로 정밀한 용량 산정(capacity planning)의 최종 근거로 쓰기보다는, 여러 설계안의 우선순위를 빠르게 좁히는 1차 필터로 쓰는 것이 적절하다.
실전 팁: 자주 하는 실수
냅킨 계산을 실전에 적용할 때 반복적으로 나타나는 실수는 크게 네 가지다 — 정밀도를 좇으려는 것, 기준 상수를 매번 새로 조사하는 것, 격차의 방향을 무시하는 것, 계산 결과 자체를 실측 없이 결론으로 삼는 것이다.
- 자릿수가 아니라 정밀도를 추구한다. 냅킨 계산은 속도와 방향성이 목적이지 소수점 단위 정확도가 목적이 아니다. “정확히 몇 ms인가"를 계산하려 들면 오히려 벤치마크보다 느리고 부정확한 결과를 얻는다. 자릿수(order of magnitude) 수준에서 멈춰야 실전에서 즉시 꺼내 쓸 수 있다.
- 기준 상수를 매번 새로 조사한다. 메모리 대역폭·디스크 지연 같은 상수를 프로젝트마다 다시 검색하면 냅킨 계산의 장점(즉시성)이 사라진다. 위 수치표처럼 자주 쓰는 값 몇 개를 미리 외워두거나 손이 닿는 곳에 정리해두는 습관이 전제 조건이다.
- 격차의 방향을 무시한다. 실측이 이론보다 느린 경우(사례 1)와 빠른 경우(사례 2)는 진단 방향이 정반대다. 느리면 구조적 병목을, 빠르면 계산에서 빠뜨린 최적화 메커니즘을 의심해야 하는데, 이 구분 없이 “격차가 크다"는 사실만 보면 엉뚱한 곳을 조사하게 된다.
- 냅킨 계산 결과를 실측 없이 최종 결론으로 쓴다. 사례 2에서 그룹 커밋의 존재를 확인한 것은 냅킨 계산이 아니라 그 뒤의 추가 조사였다. 냅킨 계산은 조사할 질문을 좁혀줄 뿐, 그 질문에 대한 답은 코드·설정을 직접 봐야 나온다.
이 방법론으로 스스로 판단할 수 있어야 하는 것
이 글을 읽고 나면 벤치마크와 냅킨 계산이 서로 어떤 역할을 나눠 맡는지, 실측치와 이론치의 격차가 어느 방향으로 벌어졌을 때 무엇을 의심해야 하는지, 그리고 이 방법론을 아예 쓰지 말아야 할 상황이 언제인지를 스스로 판단할 수 있어야 한다. 구체적으로는 다음 세 가지다.
- 냅킨 계산과 벤치마크의 역할 차이를 설명할 수 있다. 벤치마크는 “지금 얼마나 빠른가"라는 실측치를 주고, 냅킨 계산은 그 실측치를 해석할 기준선(이론 상한)을 준다. 벤치마크 수치만 있으면 그 수치가 좋은지 나쁜지 판단할 근거가 없다는 점, 그래서 둘은 경쟁 관계가 아니라 냅킨 계산이 먼저 오고 벤치마크가 그 뒤를 검증하는 순서 관계라는 점을 구분할 수 있어야 한다.
- 격차의 방향만 보고 병목의 종류를 좁힐 수 있다. 실측이 이론보다 훨씬 느리면(사례 1의 10초 vs 10밀리초) 계산에 포함하지 않은 아키텍처 수준 오버헤드(분산 통신, 조정 비용)를 의심해야 하고, 실측이 이론보다 빠르면(사례 2의 초당 5,300건 vs 1,000건) 계산에 넣지 않은 최적화 메커니즘(배칭, 캐싱, 그룹 커밋류)이 이미 작동 중이라고 의심해야 한다. 이 둘을 헷갈리면 엉뚱한 방향을 조사하게 된다.
- 냅킨 계산이 적절하지 않은 상황을 스스로 구분할 수 있다. 병목 위치가 이미 명확하거나, 원인이 하드웨어 물리 한계가 아니라 로직 버그·설정 실수처럼 순수 소프트웨어적인 문제라면 냅킨 계산 대신 직접 디버깅이 더 빠르다. 또한 자릿수 단위의 어림값이므로 정밀한 용량 산정의 최종 근거로 쓰기에는 부족하다는 것도 구분할 수 있어야 한다.
요약
Napkin math는 벤치마크를 돌리기 전에 메모리 대역폭·디스크 fsync 지연 같은 하드웨어 1차 원리로 이론적 성능 상한을 암산 수준으로 먼저 계산해두는 습관이다. Turbopuffer의 Simon Eskildsen이 Shopify에서 검색 쿼리·MySQL 트랜잭션 처리량을 분석하며 이 방법으로 병목의 위치를 좁혔던 두 사례, 그리고 같은 시기 Shopify에서 나온 durability 원칙과 toxiproxy까지 함께 놓고 보면, 이 방법론의 본질은 결국 “그럴듯해 보이는 것"과 “실제로 검증된 것"을 구분하려는 하나의 태도로 수렴한다.
참고 자료
- The Pragmatic Engineer, “Pushing software engineering limits, with Simon Eskildsen” (2026-07-21): https://newsletter.pragmaticengineer.com/p/pushing-software-engineering-limits
- GitHub: sirupsen/napkin-math (기준 수치 저장소, 2026-03-08 최신 갱신): https://github.com/sirupsen/napkin-math
- GitHub: Shopify/toxiproxy README (toxiproxy 목적·2014-10 도입 시점): https://github.com/Shopify/toxiproxy
- Simon Eskildsen 소개(Turbopuffer 공동창업자 겸 CEO, Shopify 경력): https://sirupsen.com/about
- Turbopuffer 회사 소개(공동창업자·연혁): https://turbopuffer.com/about
![Featured image of post [Programming] Napkin Math — 벤치마크 전에 하드웨어 성능 상한 암산하기](/post/2026-08-04-napkin-math-performance-estimation/wordcloud_hu_92fe836e49d5cbb0.webp)
![[Monitoring] p95·p99 레이턴시란: 평균 대신 백분위수를 써야 하는 이유](/post/2026-07-22-p95-p99-latency-percentile-guide/wordcloud_hu_92829f34cb3ed682.webp)
![[Performance] 지연 시간 메트릭 마스터하기: P90, P95, P99](/post/2024-09-09-latency-metrics/wordcloud_hu_6847a4fbb17f3a81.webp)
![[Hardware] LattePanda Alpha에 Ubuntu 16.04 LTS 설치 가이드](/post/2018-12-06-install-ubuntu-16.04-on-lattepanda/wordcloud_hu_fc536f8de2cbd4bf.webp)
![[Optimization(Series)] Introduction: Low-latency 최적화 12트랙 로드맵](/post/low-latency-optimization-series/getting-started-low-latency-optimization-series-overview/wordcloud_hu_8a1f40e0771bebe4.webp)
![[Performance 04] Introduction: Low-latency 메모리·할당·레이아웃](/post/memory-optimization/getting-started-memory-allocation-data-layout-tuning/wordcloud_hu_4b3d1ede294a01c.webp)