场景题:排行榜怎么设计?

刷到此贴的友友春招/暑期必上岸!!!

鼠鼠在秋招的过程中多次被问到场景题,中大厂的考察频率相当之高,一般会放在最后一个问题用来拖时间,也遇到过上来就问你怎么设计一个系统(面试官以此来决定后面对你的态度)。所以鼠鼠准备开这个场景题栏目,分享在秋招过程中遇到的场景题以及如何进行回答,感兴趣和感觉有帮助的友友点个关注和赞吧,你们的点赞和关注是鼠鼠持续更新下去的最大动力!!!

话不多说开启今天的主题,排行榜设计吧!!!

排行榜是很常见的一个功能,在社交软件、游戏等各种场景中都有应用,积分、点赞、礼物、战绩排名等各类排行榜功能,这些排行本质都是基于计数进行排序的。不同的场景会有细微的设计差异,这里只讲通用的排行榜系统该如何设计,遇到具体的场景再做细微的调整即可,就算在面试过程中只能答出本文所设计的通用排行榜,也足够了,毕竟对于应届生也只会考察到这个程度,面试是尽可能多的回答问题,很难追求所有问题都能回答出来……

大家可能看过一些八股文,会回答直接使用zset进行试试排行即可。

鼠鼠也曾在面试中这样回答过:将每个用户的得分作为zset中元素的score,将用户ID作为元素的value。使用zset提供的排序功能,可以按照分数从高到低排序。

当时面试官说如果分数相同,按照默认的排序规则会按照value值排序,他希望按照时间顺序排序,也就是分数相同的情况下先上榜的排在前面。

当时把鼠鼠给难住了,面完后才找到一个可行的方案:

为了实现分数相同按照时间顺序排序,可以将分数score设置为一个浮点数,其中整数部分为得分,小数部分为时间戳

即:score = 分数 + 1 - 时间戳/1e13

此时在分数相同的情况下,时间早的时间戳小,除以一个很大的数后得到的数字就小,被1减去以后得到的差就会大,也就实现了

分数相同的情况下先上榜的排在前面。

但面试官后面希望我聊一些系统设计的思路,当时鼠鼠完全没有系统设计的思路,不管后面复盘后也总结出了一套方法论,在这里分享给大家。

(1)明晰项目诉求:在这里就是设计出一个根据积分或点赞等数据进行排序。同时关注请求量,是否需要做高并发/高可用的扩展设计;此外对实时性是否也要要求,追求强一致性还是最终一致性

(2)确定业务逻辑:新用户上榜后排行榜要产生变化;用户积分发生变化后调整排名

(3)架构设计:存储(MySQL/Redis)+服务(是否需要拆分为多个服务)

大体上排行榜由两部分组成,排序结构和信息汇总结构。也就是我们在排行榜上看到的根据点赞数排出前一百,而信息汇总则是我们点击某一个用户头像可以看到其具体的用户信息。 系统设计初期,前端同步调用排行榜系统,对于并发量不大的情况,可以直接使用MySQL作为存储,直接操作数据库io即可,这里数据库的极限在5000/s。也可以先把全量数据从数据库里取出来后在内存中进行排序(前提是数据量不大的情况下)

但随着并发量和用户量上升,这种强依赖的同步调用会增加接口延迟。 这时可以增加中间层,也就是应对接口性能提不上去的三板斧之一(缓存,消息队列,分库分表)。如使用Rocket MQ或Kafka等消息队列(MQ)。流量大时可对排行榜系统起到削峰作用,还可批量插入数据库减少IO次数,提高插入效率。不过,使用MQ后要做好幂等处理(八股提问,MQ的消息幂等有哪些方式可以实现)。 当流量和并发量持续上升,数据库读写锁竞争加剧,可采用主从分离等方式均摊读压力,当然也可以直接考虑使用Redis作为排行榜。利用Redis的sortset类型排序(这里需要掌握zset,相关的八股文也要熟悉,可能会被问到),如排行评论数可使用ZINCRBY命令更新,查询用ZREVRANGE命令获取前N名排名和分数。 架构上可以由Redis作为消费者,它订阅MQ消息,消费时做幂等判断,用Lua脚本保证操作原子性。(这段话可以作为经典话术使用)

总结:

针对排行榜,简单的就直接可以使用Redis排序,但如果需要保证时间戳小的在前面就需要做一点小处理。

面对设计一个通用的排行榜系统,考察系统设计能力,这里就可以从我前面列举的方法论进行展开,多多关注我的文章,积累经验,相信友友们一定会越来越游刃有余。

PS:

其实在整个分析过程中大家可以发现,场景题其实就会把我们背的那些八股和技术运用起来,所以在学习场景题的时候就可以把八股文进行问题,有点像单词背不住就去读阅读文章,在读文章的时候记住八股文,在上面的分析过程中我也有几处进行了随机的八股提问。排行榜这个过程系统设计过程中有用到MQ,那友友们是不是可以顺带复习一下MQ的相关八股呢?

(1)如何保证MQ的消息幂等性?

(2)MQ的推模式和拉模式是什么?

(3)如何保证MQ消息不丢?

……

以上都是鼠鼠在面试中只要遇到Redis就一定会被问到的,不一定是全部问到,但至少都是三选一了…

好了如果大家有什么问题的话欢迎来评论区交流。包括但不限于文章创作改正意见,后续分享内容(面经,知识输出,经验分享等等),都看到这了,点个免费的关注和赞不过分吧

#场景题##八股文##面试##暑期实习##春招#
全部评论
时间戳处理很妙
5 回复 分享
发布于 03-27 20:46 湖北
1e13 这个是怎么确定的
1 回复 分享
发布于 03-31 13:13 江西
1 回复 分享
发布于 03-27 22:34 北京
m
点赞 回复 分享
发布于 04-30 12:54 四川
m
点赞 回复 分享
发布于 04-21 09:56 四川
催更催更催更
点赞 回复 分享
发布于 04-15 15:21 陕西
点赞 回复 分享
发布于 04-04 16:05 福建
优秀
点赞 回复 分享
发布于 04-03 13:02 广东
排行榜用 mq 没太看明白,可以解释一下吗
点赞 回复 分享
发布于 04-01 16:55 广东
点赞 回复 分享
发布于 04-01 16:17 上海
mark
点赞 回复 分享
发布于 04-01 06:19 上海
点赞 回复 分享
发布于 03-31 12:56 浙江
mark住Redis部分
点赞 回复 分享
发布于 03-31 09:18 湖北

相关推荐

查看9道真题和解析 简历中的项目经历要怎么写
点赞 评论 收藏
分享
头像
05-09 16:22
已编辑
华南师范大学 Java
  一面四小时后通知次日二面——————————🧠 个人背景与项目经历1.XX系统是你们这边的项目吗?你一直在做这个项目吗?2.做过一个XX项目是吧?是学习项目还是公司项目?3.项目中你主要负责了什么?4.你参与的项目经验多吗?5.除了XX和XX系统,有没有别的项目可以讲讲?💻 技术能力 - 后端开发6.数据库与安全7.你们系统是怎么存储用户密码的?8.单纯用 MD5 会有撞库风险,如何防御?9.接口调用怎么验证调用方身份?10.使用 MD5 校验上传文件的目的是什么?☕Java & Spring11.Spring Boot 用了哪些 starter?各自的作用是什么?12.如果第三方 starter 功能不够怎么办?13.Spring Boot 中有没有用到 AOP?14.可以用来扩展 starter 的方式有哪些?15.Spring 全家桶覆盖的范围够用吗?多线程与线程安全16.ConcurrentHashMap 为什么线程安全?17.JDK1.8 之前和之后的实现有何区别?18.size() 方法是怎么统计的?是否加锁?🔐 安全性与权限控制19.上传文件前需要做哪些安全校验?接口安全20.接口层面做了哪些安全处理?21.JWT 是怎么生成的?22.JWT 是用哪个库实现的?签名算法是什么?23.Token 刷新的触发机制是什么?24.项目中有没有做 token 自动续期?幂等性25.接口幂等性有哪些实现方式?⚙️ 系统架构与中间件26.Redis 与缓存机制27.什么是缓存穿透?怎么解决?28.什么是缓存击穿?怎么解决?29.什么是缓存雪崩?怎么解决?30.热 key 会带来什么问题?如何应对?MQ & 延迟任务31.用 MQ 实现了什么业务?32.如何通过 MQ 做延迟队列?解决了什么问题?🧱 设计模式33.工厂模式和抽象工厂模式的区别是什么?34.代理模式和装饰器模式有什么不同?🧠 Java 基础知识35.Java 能否继承多个类?36.接口中能定义实现方法吗?JDK8 之后呢?37.接口中 default 方法你了解吗?🧪 Linux 运维基础38.在 Linux 下怎么查看远程端口是否可达?39.除了 telnet 还有什么命令可以测试端口?(比如 nc)
点赞 评论 收藏
分享
评论
76
318
分享

创作者周榜

更多
牛客网
牛客企业服务