Java Concurrent Programming 第二篇

一:多线程的2种实现方式

1: 继承Thread类

class MyThread1 extends Thread {
    
    public void run() {
        System.out.println("我是多綫程1");
    }
}
public class Test1 {

    public static void main(String[] args) throws InterruptedException {
        MyThread1 thread1=new MyThread1();
        thread1.start();
    }

}

2:实现Runnable接口

class MyThread2 implements Runnable {
    @Override
    public void run() {
        System.out.println("我是多线程2");
    }
}

public class Test1 {

   public static void main(String[] args) throws Exception {

        MyThread2 mt = new MyThread2();
        Thread t1 = new Thread(mt);
        t1.start();  

 }

}

3:Join方法的使用

Thread t1 = new Thread(new Runnable() {
            @Override
            public void run() {
                for (int i = 0; i < 5; i++) {
                    System.out.print(Thread.currentThread().getName() + "  ");
                    try {
                        Thread.sleep(50);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
            }
        });
        Thread t2 = new Thread(new Runnable() {
            @Override
            public void run() {
                for (int i = 0; i < 5; i++) {
                    System.out.print(Thread.currentThread().getName() + "  ");
                    try {
                        Thread.sleep(50);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }

                }
            }
        });

        t1.start();
        t1.join();
        t2.start();

二:ThreadGroup

class MyThread extends Thread
{
    public MyThread(ThreadGroup tg, String name) {
        super(tg, name);
    }

    public void run() {
        System.out.println("ThreadName = " + Thread.currentThread().getName() + "准备开始死循环了");
        while (!this.isInterrupted()) {
        }
        System.out.println("ThreadName = " + Thread.currentThread().getName() + "结束了");
    }
}
public class Test1 {

    public static void main(String[] args) throws InterruptedException {
        ThreadGroup tg = new ThreadGroup("我的线程组");//创建一个线程组 ThreadGroup(ThreadGroup parent, String name)
        MyThread mt = null;
        for (int i = 0; i < 3; i++) {
            mt = new MyThread(tg, "线程" + i);//将线程加入到线程组去
            mt.start();
        }
        Thread.sleep(2000);
        System.out.println("线程组活跃数:"+tg.activeCount());//返回线程组的活跃线程数
        tg.interrupt();//中断线程组
        System.out.println("调用了interrupt()方法");
    }

三:ThreadPoolExecutor

      //ThreadPoolExecutor(corePoolSize,maximumPoolSize,keepAliveTime,TimeUnit,workQueue,RejectedExecutionHandler);


       ThreadPoolExecutor pool = new ThreadPoolExecutor(10, 30, 30, TimeUnit.MINUTES,
                new ArrayBlockingQueue<Runnable>(10), new AbortPolicy());

        for (int i = 1; i < 100; i++) {
            System.out.println("提交第" + i + "个任务");
            pool.execute(new Runnable() {
                @Override
                public void run() {
                    try {
                        System.out.println(">>>task is running========");
                        TimeUnit.SECONDS.sleep(10);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
            });
        }

        pool .shutdown();
        if(!pool .awaitTermination(10, TimeUnit.SECONDS)) {
            List<Runnable> runnables=pool .shutdownNow();
        }

参数名作用
corePoolSize核心线程池大小
maximumPoolSize最大线程池大小
keepAliveTime线程池中超过corePoolSize数目的空闲线程最大存活时间;可以allowCoreThreadTimeOut(true)使得核心线程有效时间
TimeUnitkeepAliveTime时间单位
workQueue阻塞任务队列
threadFactory新建线程工厂
RejectedExecutionHandler当提交任务数超过maxmumPoolSize+workQueue之和时,任务会交给RejectedExecutionHandler来处理
1:当线程池小于corePoolSize时,新提交任务将创建一个新线程执行任务,即使此时线程池中存在空闲线程。
2:当线程池达到corePoolSize时,新提交任务将被放入workQueue中,等待线程池中任务调度执行。
3:当workQueue已满,且maximumPoolSize>corePoolSize时,新提交任务会创建新线程执行任务。
4:当提交任务数超过maximumPoolSize时,新提交任务由RejectedExecutionHandler处理。
5:当线程池中超过corePoolSize线程,空闲时间达到keepAliveTime时,关闭空闲线程。
6:当设置allowCoreThreadTimeOut(true)时,线程池中corePoolSize线程空闲时间达到keepAliveTime也将关闭。

(1)workQueue

//LinkedBlockingQueue,ArrayBlockingQueue  的区别

阻塞队列LinkedBlockingQueue和ArrayBlockingQueue的区别 - 简书

SynchronousQueue:
这个队列接收到任务的时候,会直接提交给线程处理,而不保留它,如果所有线程都在工作,那就新建一个线程来处理这个任务.使用这个类型队列的时候,maximumPoolSize一般指定成Integer.MAX_VALUE。
LinkedBlockingQueue:
这个队列接收到任务的时候,如果当前线程数小于核心线程数,则新建线程(核心线程)处理任务;如果当前线程数等于核心线程数,则进入队列等待。由于这个队列没有最大值限制(新版本可以指定容量,如果不指定容量,默认是Integer.MAX_VALUE),即所有超过核心线程数的任务都将被添加到队列中,这也就导致了maximumPoolSize的设定失效,因为总线程数永远不会超过corePoolSize。
ArrayBlockingQueue:
可以限定队列的长度,接收到任务的时候,如果没有达到corePoolSize的值,则新建线程(核心线程)执行任务,如果达到了,则入队等候,如果队列已满,则新建线程(非核心线程)执行任务,又如果总线程数到了maximumPoolSize,并且队列也满了,则发生错误。

(2)RejectedExecutionHandler

AbortPolicy :
默认。直接抛异常。
CallerRunsPolicy :
只用调用者所在的线程执行任务,重试添加当前的任务,它会自动重复调用execute()方法,
调用者线程性能可能急剧下降。
DiscardOldestPolicy :
丢弃任务队列中最久的任务。
DiscardPolicy :
丢弃当前任务。

自定义方式

class CustomRejectedExecutionHandler implements  RejectedExecutionHandler {
 
    @Override
    public void rejectedExecution(Runnable r, ThreadPoolExecutor executor) {
        //改成put阻塞方法
        try {
            executor.getQueue().put(r);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}

四:java自带的几种线程池

1:newCachedThreadPool

ExecutorService cachedThreadPool = Executors.newCachedThreadPool();//coreSize:0; 默认最大size是Integer.MAX_VALUE
        
        for (int i = 0; i < 10; i++) {
            cachedThreadPool.execute(new Runnable() {
                @Override
                public void run() {
                    System.out.println("run");
                }
            });
        }

2:newFixedThreadPool 

ExecutorService fixthreadPool = Executors.newFixedThreadPool(2);
        
        for (int i = 0; i < 10; i++) {
            fixthreadPool.execute(new Runnable() {
                @Override
                public void run() {
                    System.out.println("run");
                }
            });
        }

3:newScheduledThreadPool 
        ScheduledExecutorService scheduledThreadPool = Executors.newScheduledThreadPool(5);

      //延时执行任务
        scheduledThreadPool.schedule(new Runnable() {

            @Override
            public void run() {
                System.out.println("delay 2 seconds");
            }
        }, 2, TimeUnit.SECONDS);
        

     //延时周期性执行任务
        scheduledThreadPool.scheduleAtFixedRate(new Runnable() {

            @Override
            public void run() {
            System.out.println("delay 1 seconds, and excute every 3 seconds");
            }
            }, 1, 3, TimeUnit.SECONDS);

4:newSingleThreadExecutor 

ExecutorService fixthreadPool = Executors.newSingleThreadExecutor();
        
        for (int i = 0; i < 10; i++) {
            fixthreadPool.execute(new Runnable() {
                @Override
                public void run() {
                    System.out.println("run");
                }
            });
        }

五:Future

//实现Callable接口
class MyThread2 implements Callable<Integer> {
    @Override
    public Integer call() throws Exception {
        return 1;
    }
}

public class Test1 {

    public static void main(String[] args) throws Exception {

        // 创建一个固定线程数的线程池
        ExecutorService executorService = Executors.newFixedThreadPool(1);
        // 自定义内部类实现Callable 执行实际运行内容
        MyThread2 oneThread = new MyThread2();
        // 开启线程
        Future<Integer> future1 = executorService.submit(oneThread);
        // 开启线程
        int num = 0;
        try {
            num = future1.get();
        } catch (Exception e) {
            e.printStackTrace();
        }
        System.out.println(num);

    }

六:CompletionService

class Task implements Callable<Integer> {
    
    Integer i;
    public Task(Integer i) {
        super();
        this.i = i;
    }

    @Override
    public Integer call() throws Exception {
        System.out.println("线程:" + Thread.currentThread().getName() + "任务i=" + i + ",执行完成!");
        return i;
    }
    
}

public class Test1 {

    public static void main(String[] args) throws Exception {

        // 开启5个线程
        ExecutorService exs = Executors.newFixedThreadPool(5);
        try {
            int taskCount = 10;
            // 结果集
            List<Integer> list = new ArrayList<Integer>();

            // 1.定义CompletionService
            CompletionService<Integer> completionService = new ExecutorCompletionService<Integer>(exs);

            // 2.添加任务
            for (int i = 0; i < taskCount; i++) {
                Future<Integer> future = completionService.submit(new Task(i + 1));
            }

            // 3.获取结果
            for (int i = 0; i < taskCount; i++) {
                Integer result = completionService.take().get();
                System.out.println("任务i==" + result + "完成!" + new Date());
                list.add(result);
            }

            System.out.println("list=" + list);
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            // 关闭线程池
            exs.shutdown();
        }

    }

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值