efs

编辑

5.新的问题与改进方案

列表项目

5.1 问题
以上的实现方案解决了主题框架的实现以及日均百万级数据的存储,已经可以初步实现创建任务、生产物料、引擎投放的功能了。

但是还有一个核心问题待处理:外展和创意日均660w的生产量,

这个量级生产量,在单机测试环境生产,耗时4小时以上的时间才能生产完成,是自动投放平台链路的瓶颈,如何缩短全链路的生产工时,如何提升生产效率,是需要解决的关键问题。

5.2 改进方案1:并发处理
► 方案:

上述实现方案中已经选取了xxl-job,利用分布式定时任务可以按照执行数据按照应用服务台数进行数据分片,多台服务器多进程级并行处理,还可以每台服务器上进行多线程处理,提升效率;

多线程实现方案就采用比较成熟的spring线程池即可,减少重复创建线程的过程。

● 前提:下游的算法标题和图片服务不是瓶颈,足够强的处理服务;

► 问题: 工作线程数设置为多少合理的问题?

● 分析:使用spring线程池,关键配置线程池的5个参数:corePoolSize、QueueCapacity、MaxPoolSize、KeepAliveSeconds、RejectedExecutionHandler,最核心的是设置corePoolSize大小

● 定位:生产外展卡片在调用算法生产之前,需要读取排期数据、车型车系数据、文章数据,这些数据获取都是读取mysql和redis以及外部服务等,是典型的IO密集型

● 原理:N核服务器,通过执行业务的单线程分析出本地计算时间为x,等待时间为y,则工作线程数(线程池线程数)设置为 N*(x+y)/x,能让CPU的利用率最大化

● 方式:Worker线程在执行的过程中,有一部计算时间需要占用CPU,另一部分等待时间不需要占用CPU,通过拆分过程,日志打印方式,确定cpu计算时间和io交互时间

● 结论:线程数=16*(168ms+210ms)/168ms ≈ 36

► 实现:

图片

● 结论:通过任务分片+多执行器多线程并行处理,可提升一定的生产外展卡片效率

5.3 改进方案2:减少IO-读取redis
改为localcache

► 方案:

生产外展卡片时候,组装请求参数,需要读取外展规格参数、车型车系等数据,把这些数据由mysql或者redis改为使用Cache来减少IO次数,提升性能;

► localcache选型:

采用Caffeine而不采用JDK自带Map,是因为Caffeine基于Guava Cache增强的新一代缓存技术,缓存性能极其出色;

JDK内置的Map可作为缓存的一种实现方式,然而严格意义来讲,其不能算作缓存的范畴。

原因如下:一是其存储的数据不能主动过期;二是无任何缓存淘汰策略;选型对比如下:

● 序列化

图片

评论区

评论已关闭