zoukankan      html  css  js  c++  java
  • 简单的自定义线程池(java)

    package threadpool_test;
    
    import java.util.concurrent.BlockingQueue;
    import java.util.concurrent.LinkedBlockingDeque;
    import java.util.concurrent.TimeUnit;
    
    /**
     * 自定义一个简单的线程池
     * 
     * ***/
    public class ThreadPool {
    
        private static final int coreThreadNum=3;//核心线程数
        private static final int maxThreadNum=8;//最大线程数
        
        private boolean working=true;//打开、关闭线程池
        private BlockingQueue<Thread> workThreads=new LinkedBlockingDeque<>(maxThreadNum);//当前工作线程
        
        private BlockingQueue<Runnable> tasks=new LinkedBlockingDeque<>(10);//任务队列
        
        public void execute(Runnable task) throws InterruptedException{
            if(task==null) throw new NullPointerException();
            int workNum=workThreads.size();
            if(workNum<coreThreadNum ){//当前工作线程少于核心线程数,立即启动一个线程进行工作
                Worker worker=new Worker(task);
                Thread thread=new Thread(worker);
                workThreads.offer(thread);//特殊值,add会抛出异常
                thread.start();
            }
            else if(tasks.size()<10){//任务池还没满,就把任务放进任务池里
                tasks.offer(task);
            }
            else if(workNum<maxThreadNum && tasks.size()==10){//任务队列满,开启多余线程来完成任务
                Worker worker=new Worker();
                Thread thread=new Thread(worker);
                System.out.println("开启新线程了"+thread.getName());
                workThreads.offer(thread);
                thread.start();
            }
            else{
                    System.out.println("放弃该任务");
                    return;
            }
        }
        
        public void shutDown(){
            this.working=false;
            for(Thread worker:workThreads){
                System.out.println("终止线程名:"+worker.getName());
                worker.interrupt();
            }
            System.out.println("终止线程池线程");
            Thread.currentThread().interrupt();
        }
        
        private class Worker implements Runnable{//任务包装类
            private Runnable task_origal;
            public Worker() {
            }
            public Worker(Runnable task) {
                this.task_origal=task;
            }
                @Override
                public void run() {
                    if(task_origal!=null)
                        task_origal.run();
                    while(working){
                        try {
                            Runnable task=tasks.take();//阻塞提取任务,阻塞状态下的中断并不会真的中断
                            task.run();
                        } catch (InterruptedException e) {
                            System.out.println("真的终止了");
                            Thread.currentThread().interrupt();
                        }
                    }
                }
                
            }
    }
    package threadpool_test;
    
    import java.util.concurrent.TimeUnit;
    /**
     * 测试类
     * **/
    public class testMain {
    public static void main(String[] args) throws InterruptedException {
        ThreadPool pool=new ThreadPool();
        for(int i=0;i<20;i++){
            pool.execute(new Task("任务"+i));
        }
        TimeUnit.SECONDS.sleep(4);
        pool.shutDown();
    }
    }

    显示结果:

    当前运行线程名:Thread-0当前任务名为:任务0
    当前运行线程名:Thread-2当前任务名为:任务2
    当前运行线程名:Thread-2当前任务名为:任务4
    当前运行线程名:Thread-2当前任务名为:任务5
    当前运行线程名:Thread-2当前任务名为:任务6
    当前运行线程名:Thread-2当前任务名为:任务7
    当前运行线程名:Thread-2当前任务名为:任务8
    当前运行线程名:Thread-2当前任务名为:任务9
    当前运行线程名:Thread-2当前任务名为:任务10
    当前运行线程名:Thread-2当前任务名为:任务11
    当前运行线程名:Thread-2当前任务名为:任务12
    开启新线程了Thread-3
    当前运行线程名:Thread-1当前任务名为:任务1
    当前运行线程名:Thread-1当前任务名为:任务14
    当前运行线程名:Thread-3当前任务名为:任务15
    当前运行线程名:Thread-3当前任务名为:任务16
    当前运行线程名:Thread-3当前任务名为:任务17
    当前运行线程名:Thread-3当前任务名为:任务18
    当前运行线程名:Thread-3当前任务名为:任务19
    当前运行线程名:Thread-0当前任务名为:任务3
    终止线程名:Thread-0
    真的终止了
    终止线程名:Thread-1
    终止线程名:Thread-2
    真的终止了
    真的终止了
    终止线程名:Thread-3
    终止线程池线程
    真的终止了

    ps:该线程池功能非常之简单,仅为了加深线程池核心原理而做。里面关于任务队列满后的处理情况,在这里直接简单的使用放弃该任务的方法;

  • 相关阅读:
    算法 python实现(二) 冒泡排序
    算法 python实现(一) 基本常识
    python 零散记录(五) import的几种方式 序列解包 条件和循环 强调getattr内建函数
    IT桔子-抓取数据
    mac中导出CSV格式在excel中乱码
    phantomJS安装
    pyquery 安装
    mac终端的命令都失效的解决方法
    Python爬虫防封杀方法集合
    python爬虫 403 Forbidden 解决方法
  • 原文地址:https://www.cnblogs.com/jkavor/p/7234965.html
Copyright © 2011-2022 走看看