美文网首页
多线程执行门店选品任务

多线程执行门店选品任务

作者: 苏打柠檬水 | 来源:发表于2022-10-26 13:36 被阅读0次

1.背景

连锁零售公司旗下有1000家门店,每个门店的选品过程都是独立的,每个门店选品执行的时间平均为30秒,单线程串行执行所有门店选品需要500分钟,因为业务上下游给的时间有限,需要减少整体的执行时间,执行时间控制在100分钟内。

2.思路

并行执行,500/100=5,同时有五家门店在选品,单台机器并发执行的能力是有限,若超过单台机器的并发能力可以用定时任务分片的方式来扩展并发能力。

3.模拟代码

3.1.门店选品

/**
 * 门店选品
 *
public class StoreSelection {

    /**
     * 门店编码
     */
    private String storeCode;

    private final static String TXT = "门店选品开始门店选品开始门店选品开始门店选品开始门店选品开始门店选品开始门店选品开始门店选品开始门店选品开始";

    public StoreSelection(String storeCode) {
        this.storeCode = storeCode;
    }

    public String select(){
        System.out.println(String.format("%s门店编码=%s的门店选品开始",  LocalDateTime.now(), storeCode));
        Base64.Encoder encoder = Base64.getEncoder();
        LocalDateTime start = LocalDateTime.now();
        LocalDateTime end = start.plusSeconds(30);
        //模拟选品过程中有异常
        if ("A10".equals(storeCode)) {
            throw new RuntimeException(storeCode + "门店选品异常请处理");
        }
        while (LocalDateTime.now().isBefore(end)) {
            //加重CPU负载
            encoder.encode(TXT.getBytes());
            //System.out.println(String.format("%s门店编码=%s的门店选品执行中", LocalDateTime.now(), storeCode));
        }
        System.out.println(String.format("%s门店编码=%s的门店选品完成", LocalDateTime.now(), storeCode));
        return  storeCode + "门店选品完成";
    }

    public static void main( String[] args ) {
        new StoreSelection("A1").select();
    }
}

3.2.连锁零售公司旗下所有门店选品

public class GroupSelection{

    public static void main( String[] args ) {
        List<String> storeCodeList = new LinkedList<>();
        for (int i = 0; i < 1000; i++) {
            storeCodeList.add("A"+i);
        }
        System.out.println("门店组选品开始");
        ExecutorService executor = Executors.newFixedThreadPool(5);
        List<Future<String>> futureList = storeCodeList.stream()
                .map(storeCode -> executor.submit(() -> new StoreSelection(storeCode).select()))
                .collect(Collectors.toList());
        while(!futureList.stream().allMatch(Future::isDone)){
            System.out.println("等待所有门店选品执行结束");
        }
        String re  = futureList.stream().map(future -> {
            try {
                return future.get();
            } catch (ExecutionException | InterruptedException e) {
                e.printStackTrace();
                return e.getMessage();
            }
        }).collect(Collectors.joining(","));
        System.out.println(re);
        System.out.println("门店组选品完成");
        executor.shutdown();
    }

}

4.隐患

4.1.随着公司的扩张门店数,线程池里的队列膨胀,可能导致OOM

5.可改进

5.1 使用CompletableFuture

5.2 日志改用slf4j

相关文章

  • 多线程执行门店选品任务

    1.背景 连锁零售公司旗下有1000家门店,每个门店的选品过程都是独立的,每个门店选品执行的时间平均为30秒,单线...

  • Kotlin:该如何实现多线程同步?

    问题背景需执行多线程任务:任务1、任务2并行执行;等全部执行完成后,执行任务3。 实现方式「多线程同步」。Kotl...

  • java多线程解析之Runnable

    为什么要使用多线程?  如果想要学好多线程,首先必须了解多线程的由来和作用。 当单线程执行任务时,假设执行单次任务...

  • iOS—多线程

    线程是用来执行任务的,线程彻底执行完任务A才能去执行任务B。为了同时执行两个任务,产生了多线程。 线程执行完毕就被...

  • 浅谈iOS中多线程开发

    目录: (一)线程与进程之间的区别 (二)为什么需要学习多线程 (三)多线程任务执行方式 (四)多线程执行的...

  • 线程与进程

    线程 线程是用来执行任务的,线程彻底执行完任务A才能去执行任务B。为了同时执行两个任务,产生了多线程。 进程 进程...

  • 多任务

    实现多任务的方式 多线程多进程协程多线程+多进程 并行:同时发起,同时执行(4核4个任务)并发:同时发起,单个执行...

  • 关于多线程的理解

    前言 线程是用来执行任务的,线程彻底执行完任务A才能去执行任务B。为了同时执行两个任务,产生了多线程。 1、什么是...

  • iOS开发多线程的概念

    1、了解多线程的思维 线程是用来执行任务的,线程彻底执行完任务A才能去执行任务B。为了同时执行两个任务,产生了...

  • UI(三十一)多线程-NSThread

    一、线程是用来执行任务的,线程彻底执行完任务A才能去执行任务B。为了同时执行两个任务,产生了多线程。 二、进程 1...

网友评论

      本文标题:多线程执行门店选品任务

      本文链接:https://www.haomeiwen.com/subject/zkonzrtx.html