Administrator
Published on 2025-03-09 / 7 Visits
0
0

如何使用 Redis 统计大量用户唯一访问量

使用Redis统计大量用户的唯一访问量(UV),最优方案是采用**HyperLogLog(HLL)**数据结构。

1. HyperLogLog 核心操作

  • 添加用户标识:使用 PFADD 命令将用户唯一标识(如用户ID、IP)添加到HLL中。
    PFADD uv:20231001 "user_id_or_ip"
    
  • 统计UV:使用 PFCOUNT 获取基数估计值。
    PFCOUNT uv:20231001
    
  • 合并数据:使用 PFMERGE 合并多个HLL键(如多天合并为周/月统计)。
    PFMERGE uv:week_45 uv:20231001 uv:20231002 ... uv:20231007
    PFCOUNT uv:week_45
    

2. 时间维度统计

  • 按天存储:为每天创建独立键,如 uv:YYYYMMDD
  • 设置过期时间:自动清理旧数据(例如保留7天):
    EXPIRE uv:20231001 604800  # 7天后过期
    
    建议在首次创建键时通过Lua脚本原子化操作:
    EVAL "redis.call('PFADD', KEYS[1], ARGV[1]); if redis.call('TTL', KEYS[1]) == -1 then redis.call('EXPIRE', KEYS[1], ARGV[2]) end; return 1;" 1 uv:20231001 "user123" 86400
    

3. 误差与性能

  • 误差率:约0.81%,适用于近似统计场景。
  • 内存占用:每个HLL键仅需约12KB,百万级UV仅需MB级内存。

4. 精确统计替代方案

若需精确UV,可选以下方法(根据场景权衡):

  • 位图(Bitmap):用户ID为连续整数时高效。
    SETBIT uv:20231001 100000 1  # 用户ID=100000访问
    BITCOUNT uv:20231001         # 统计总数
    
  • 集合(Set):小数据量时直接存储。
    SADD uv:20231001 "user_id"
    SCARD uv:20231001
    
  • 布隆过滤器 + 计数:需额外维护计数。

5. 分维度统计

在键名中加入业务标识,如页面或产品:

PFADD uv:homepage:20231001 "user_id"
PFCOUNT uv:homepage:20231001

总结

  • 推荐方案:使用HyperLogLog实现低内存消耗的近似UV统计。
  • 适用场景:允许误差的实时或大数据量统计(如DAU、活动参与数)。
  • 注意事项:合理设置键过期时间,避免内存累积;合并数据时直接使用 PFMERGE

通过上述方法,Redis能够高效处理海量用户的UV统计需求,平衡内存占用与性能。


Comment