java手写线程池用于处理异步任务

由于最近业务上有需求,业务逻辑的一个数据下发功能需要改为异步执行,以免耽误主业务的执行,刚开始每次都新建一个线程,并发大了线程频繁开启并且不好控制,所以打算使用jdk自带的线程池ThreadPoolExecutor实现,

然后自己根据jdk实现的写了个简单的线程池玩玩

package com.wying.threadPool;

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.LinkedBlockingQueue;
import java.util.concurrent.atomic.AtomicLong;

/**
 * description:自定义线程池学习
 * date: 2020/7/13
 * author: gaom
 * version: 1.0
 */
public class MyTestPool {

    //最大线程数
    private static final int maxThreadNum = 10;

    //最小线程数
    private static final int minThreadNum = 1;
    //工作队列
    private BlockingQueue<Runnable> taskQueue = new LinkedBlockingQueue<>();
    //工作者线程池
    private List<Worker> workerList = Collections.synchronizedList(new ArrayList<>());
    //当前线程数
    private int workerNum ;


    private AtomicLong threadNumber = new AtomicLong();

    public MyTestPool(int initNum){

        //初始化工作线程
        this.workerNum = initNum > maxThreadNum ? maxThreadNum
                : initNum  <  minThreadNum ?  minThreadNum : initNum;
        System.out.println("初始化线程池 欲初始化initNum:"+initNum+" 实际初始化数量:"+this.workerNum);
        init(workerNum);

    }
    private void init(int workerNum) {

        for (int i = 0; i < workerNum; i++) {
            workerList.add(new Worker("我的工作编号:" + threadNumber.incrementAndGet()));
        }
        for (Worker worker : workerList) {
            new Thread(worker).start();
        }
    }

    //执行任务
    public void execute(Runnable runnable) {
        if (runnable != null) {
            synchronized (taskQueue) {
                //加入任务到队列
                taskQueue.add(runnable);
                //同时唤醒 调用wait堵塞了读取队列的线程
                taskQueue.notifyAll();
            }
        }
    }


    //关闭线程池
    public void shutdown() {
        for (Worker worker : workerList) {
            worker.shutdown();
        }
    }

    private class Worker implements Runnable {
        private volatile boolean isStop = false;
        private String workerName = "";

        public Worker(String workerName) {
            System.out.println("初始化了一个新的线程 workerName:"+workerName);
            this.workerName = workerName;
        }

        //开启的N个线程不断从任务队列读取是否有新任务
        @Override
        public void run() {
            //工作者是否工作开关
            while (!isStop) {
                Runnable runnable = null;
                //由于并发线程安全问题 需要加锁
                synchronized (taskQueue) {
                    while (taskQueue.isEmpty()) {
                        try {
                            //如果没有任务 则调用wait等待 此时会堵塞所有的线程
                            taskQueue.wait();
                        } catch (InterruptedException e) {
                            Thread.currentThread().interrupt();
                            return;
                        }
                    }
                    //任务列表不为空 获取任务
                    runnable = taskQueue.poll();
                }
                //当有任务时 调用notifyAll后 该线程继续工作
                if (runnable != null) {
                    try {
                        System.out.println(this.workerName+ " 开始执行任务 ");
                        //执行任务
                        runnable.run();
                        System.out.println(this.workerName+ " 任务执行完毕 ");
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                }
            }
        }

        public void shutdown() {
            this.isStop = true;
            System.out.println(this.workerName + " is shutdown");
        }
    }

    public static void  main(String  args[]) {
        MyTestPool myTestPool = new MyTestPool(3);
        myTestPool.execute(new Runnable() {
            @Override
            public void run() {
                System.out.println("我需要去搬砖 预计耗时5S "+Thread.currentThread().getId());
                try {
                    Thread.sleep(5000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }

            }
        });

        myTestPool.execute(new Runnable() {
            @Override
            public void run() {
                System.out.println("我需要去买酒  预计耗时10S "+Thread.currentThread().getId());
                try {
                    Thread.sleep(10000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }

            }
        });

        myTestPool.execute(new Runnable() {
            @Override
            public void run() {
                System.out.println("我需要去送货  预计耗时8S "+Thread.currentThread().getId());
                try {
                    Thread.sleep(8000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }

            }
        });
/*
        for(int t=0;t<30;t++){
        myTestPool.execute(new Runnable() {
            @Override
            public void run() {
                System.out.println("测试任务  查看执行的线程id"+Thread.currentThread().getId());
                try {
                    Thread.sleep(500);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }

            }
        });
        }*/
    }


}

执行结果

初始化了2个线程 并添加了3个任务,工作编号1执行完第1个任务后,在执行第3个任务,保证不管有多少任务添加到任务队列,

都是固定的一批线程在处理。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值