用Redis玩转点赞,数据结构和效率那些事儿聊聊
- 问答
- 2026-01-21 22:19:00
- 3
综合自互联网技术博客与社区讨论,如CSDN、掘金、知乎等平台的常见技术分享)

今天咱们就来聊聊怎么用Redis这个好东西来搞定点赞功能,你想啊,现在哪个App没个点赞、喜欢、顶一下的功能?要是用传统的关系型数据库,比如MySQL,每次点赞都去update一下表的like_count字段,高并发的时候数据库肯定吃不消,慢死了,还容易把表锁住,Redis是内存数据库,速度飞快,而且它提供了好几种特别适合玩转点赞的数据结构。
最直接想到的可能是用String(字符串)类型,给每个文章或者每条微博设置一个key,像这样:post:123:like_count,value就是点赞的数量,用户点一下赞,我们就用INCR命令给这个值加1;取消点赞就用DECR减1,查询数量也很简单,直接GET这个key就行了,这个方法简单是简单,但是有个大问题:我们没法记录具体是哪个用户点的赞,万一有黑粉或者水军来回点赞、取消点赞刷数据,我们就没法判断了,因为只知道总数,不知道细节。

更常用的方法是使用Set(集合),Set的特点就是里面的元素都是唯一的,不能重复,这不正好对应一个用户只能点一次赞的规则吗?我们可以为每个被点赞的对象(比如文章ID为123)创建一个Set,key可以叫post:123:liked_users,每当用户ID为456的用户点了赞,我们就执行SADD post:123:liked_users 456,把这个用户ID塞进集合里,取消点赞就是SREM post:123:liked_users 456,这样设计好处太多了:
第一,可以完美防止重复点赞,因为同一个用户在集合里只能存在一次,SADD命令对于已存在的成员会直接忽略。
第二,查询点赞总数直接用SCARD post:123:liked_users,这个命令能瞬间返回集合的元素个数,也就是总点赞数。
第三,可以轻松判断当前用户是否已经点过赞了,用SISMEMBER post:123:liked_users 456,返回1就是点过,0就是没点过,前端可以根据这个状态来显示不同的按钮样式(比如实心爱心还是空心爱心)。
第四,甚至还能用SMEMBERS命令(小心使用,如果成员太多会阻塞)或者更优的SSCAN命令来获取所有点赞用户的列表,方便做一些排行榜或者显示最近点赞的人之类的功能。
那有没有比Set更好的办法呢?有时候我们可能不仅需要知道谁点了赞,还想知道点赞的时间顺序,比如要展示“最近点赞的3个人”,这时候Sorted Set(有序集合)就派上用场了,它和Set一样保证成员唯一,但每个成员都会关联一个分数(score),我们可以把用户ID作为成员,把点赞时的时间戳(比如timestamp)作为分数,点赞操作就是ZADD post:123:liked_users_with_time timestamp 456,这样,当我们想获取最近点赞的N个用户时,就可以用ZREVRANGE post:123:liked_users_with_time 0 2,意思是按照分数从大到小(也就是时间从近到远)取出排名前3(索引0到2)的成员,点赞总数和判断是否点过赞的命令和Set类似,是ZCARD和ZSCORE(看分数是否存在),Sorted Set功能更强大,但因为它需要为每个成员存储一个分数,所以占用的内存通常会比普通的Set要大一点点,这就需要根据实际需求来权衡了。
除了核心的点赞动作,我们还得考虑数据持久化和与数据库同步的问题,Redis的数据在内存里,万一服务器重启了,数据可能就丢了(除非配置了持久化策略),所以一般的做法是,把Redis当作一个高速的计数器缓存,真实的点赞数据最终还是要落地到MySQL这样的数据库里的,怎么同步呢?通常不是每次点赞操作都去写一次数据库,那样又慢了,可以采用异步的方式,比如定时任务,每隔一段时间(比如每5分钟)把Redis里各个文章的点赞数量增量同步到数据库的like_count字段上,或者通过消息队列,把点赞事件发出去,再由一个消费者慢慢去更新数据库,这样既保证了前端的极速响应,又保证了数据的最终一致性。
最后还得考虑一些特殊情况,比如热Key问题,如果有一篇超级爆款文章,瞬间几万人点赞,那么对post:爆款文章ID:liked_users这个Key的操作会全部打到Redis集群的某一个节点上,可能导致这个节点压力过大,解决的办法可以是对Key进行散列,比如在Key后面加上随机后缀,把数据分散到多个Key上,但这样查询总数的时候就得聚合计算,稍微麻烦点。
用Redis做点赞,核心思想就是利用其内存高速读写和丰富的数据结构特性,把最频繁的操作放在Redis里完成,然后再想办法把数据稳妥地同步到硬盘数据库里,Set结构是最常用、最省心的选择,如果需要时间排序再考虑Sorted Set,这样一套下来,点赞功能就能又快又稳。

本文由帖慧艳于2026-01-21发表在笙亿网络策划,如有疑问,请联系我们。
本文链接:http://www.haoid.cn/wenda/84222.html
