bigywater.tech
Flask · 168

缓存命中率

缓存命中率受什么影响?容量、访问分布、TTL 各自有多大作用?怎么在线上看命中率?这篇用一个有热点的访问序列和真实的 redis,把每个因素的影响量出来。

33% → 84%
缓存容量从 100 增到 5000 时的命中率(Zipf 访问)
55% vs 5%
同样容量 500:有热点与均匀随机访问的命中率
keyspace_hits
redis 自己统计命中的 INFO 字段

容量与命中率

实测 · 本机执行输出
      容量     命中率            平均耗时(未命中 5 ms,命中 0.05 ms)
     100   33.4%                           3.35 ms
     500   54.8%                           2.29 ms
    2000   74.3%                           1.32 ms
    5000   84.0%                           0.84 ms

上一篇:连接池大小;下一篇:大文件响应性能。

访问序列是我生成的 Zipf 分布(固定随机种子),不是真实流量;命中与未命中的耗时(0.05 ms 与 5 ms)是假设值。TTL 一节用模拟时钟,不是真的等了 20 秒。

访问分布

实测 · 本机执行输出
  Zipf(有热点)      命中率 54.8%
  均匀随机           命中率 5.2%

过期时间

实测 · 本机执行输出
  TTL 0.05 秒   命中率 53.6%
  TTL 0.5 秒    命中率 53.6%
  TTL 1 秒      命中率 53.6%
  TTL 2 秒      命中率 63.0%
  TTL 5 秒      命中率 72.9%
  TTL 10 秒     命中率 78.9%
  TTL 不过期      命中率 84.0%

redis 的命中统计

实测 · 本机执行输出
  应用侧统计命中率 81.5% | redis 的 keyspace_hits 16300、keyspace_misses 3700 → 81.5% | evicted_keys 1650 | 当前 key 数 2050,已用内存 1.27M

redis 是自己在非默认端口起的临时实例,验证完就关闭了。

分步演示

缓存命中率
本步的对象

    本文用到的工具与边界

    • 本机 macOS 27 arm64 / Python 3.14.7 / Flask 3.1.3 / Werkzeug 3.1.9 / Jinja2 3.1.6 / SQLAlchemy 2.1.1 / gunicorn 26.2.0(都装在自己的虚拟环境里);大多数实验用 Flask 的 test_client(直接调用 WSGI 应用,不经过网络),需要真实 HTTP 时另起 gunicorn 或开发服务器(端口 9600 以上,本机 127.0.0.1);计时用 time.perf_counter,数字每次运行会有小幅抖动。cachelib SimpleCache、redis-py 8.1.0、自己起的 redis
    • 没有验证:真实业务流量的访问分布、Flask-Caching 自身的统计接口、缓存穿透与雪崩(第 75 篇看过击穿)、多级缓存、容量按字节计的内存缓存、W-TinyLFU 等更复杂的淘汰策略
    京ICP备2026067502号-1京公网安备11010502063487号