线程数

Java并发编程:线程池的使用

亡梦爱人 提交于 2019-12-02 19:48:27
转载自:http://www.cnblogs.com/dolphin0520/p/3932921.html Java并发编程:线程池的使用   在前面的文章中,我们使用线程的时候就去创建一个线程,这样实现起来非常简便,但是就会有一个问题:   如果并发的线程数量很多,并且每个线程都是执行一个时间很短的任务就结束了,这样频繁创建线程就会大大降低系统的效率,因为频繁创建线程和销毁线程需要时间。   那么有没有一种办法使得线程可以复用,就是执行完一个任务,并不被销毁,而是可以继续执行其他的任务?   在Java中可以通过线程池来达到这样的效果。今天我们就来详细讲解一下Java的线程池,首先我们从最核心的ThreadPoolExecutor类中的方法讲起,然后再讲述它的实现原理,接着给出了它的使用示例,最后讨论了一下如何合理配置线程池的大小。   以下是本文的目录大纲:   一.Java中的ThreadPoolExecutor类   二.深入剖析线程池实现原理   三.使用示例   四.如何合理配置线程池的大小    若有不正之处请多多谅解,并欢迎批评指正。   请尊重作者劳动成果,转载请标明原文链接:   http://www.cnblogs.com/dolphin0520/p/3932921.html   一.Java中的ThreadPoolExecutor类   java.uitl

线程池参数设置

雨燕双飞 提交于 2019-12-02 19:47:31
在如今的多核处理器时代,多线程技术发挥着巨大的作用,尤其对于大批量处理同类型IO密集型的任务,例如全库全表查找数据时,多线程是提升速度和性能的利器。 近期发布的另一篇文章已经详细介绍了线程池的技术原理。但平时的开发工作中,我们可能更加关注的是线程池的使用,线程数设置多大啊?队列大小设置多大啊,等问题。 这篇文章主要是针对前段时间对线程池的使用过程中,总结了几点参数设置方面的建议,希望对大家有用。 使用多线程时,会面临 线程数,队列大小( corePoolSize maxPoolSize queueCapacity ) 三个重要参数的大小设置问题。 我根据自己前期的工作总结发现参数设置主要考虑下面几个方面: 1. 线程池中执行的任务性质 。 计算密集型的任务比较占cpu,所以一般线程数设置的大小 等于或者略微大于 cpu的核数;但IO型任务主要时间消耗在 IO等待上,cpu压力并不大,所以线程数一般设置较大,例如 多线程访问数据库,数据库有128个表,可能就直接考虑使用128个线程。 2. CPU使用率 。 当线程数设置较大时,会有如下几个问题: 第一 ,线程的初始化,切换,销毁等操作会消耗不小的cpu资源,使得cpu利用率一直维持在较高水平。 第二 ,线程数较大时,任务会短时间迅速执行,任务的集中执行也会给cpu造成较大的压力。 第三 , 任务的集中支持

Java线程池及配置参数详解

∥☆過路亽.° 提交于 2019-12-02 19:46:52
一、线程池的优点 合理利用线程池能够带来三个好处。 第一:降低资源消耗。通过重复利用已创建的线程降低线程创建和销毁造成的消耗。 第二:提高响应速度。当任务到达时,任务可以不需要的等到线程创建就能立即执行。 第三:提高线程的可管理性。线程是稀缺资源,如果无限制的创建,不仅会消耗系统资源,还会降低系统的稳定性,使用线程池可以进行统一的分配,调优和监控。 二、线程池的创建 //参数初始化 private static final int CPU_COUNT = Runtime.getRuntime().availableProcessors(); //核心线程数量大小 private static final int corePoolSize = Math.max(2, Math.min(CPU_COUNT - 1, 4)); //线程池最大容纳线程数 private static final int maximumPoolSize = CPU_COUNT * 2 + 1; //线程空闲后的存活时长 private static final int keepAliveTime = 30; //任务过多后,存储任务的一个阻塞队列 BlockingQueue<Runnable> workQueue = new SynchronousQueue<>(); //线程的创建工厂

Java线程池使用说明

一个人想着一个人 提交于 2019-12-02 19:46:28
Java线程池使用说明 一 简介 线程的使用在java中占有极其重要的地位,在jdk1.4极其之前的jdk版本中,关于线程池的使用是极其简陋的。在jdk1.5之后这一情况有了很大的改观。Jdk1.5之后加入了java.util.concurrent包,这个包中主要介绍java中线程以及线程池的使用。为我们在开发中处理线程的问题提供了非常大的帮助。 二:线程池 线程池的作用: 线程池作用就是限制系统中执行线程的数量。 根据系统的环境情况,可以自动或手动设置线程数量,达到运行的最佳效果;少了浪费了系统资源,多了造成系统拥挤效率不高。用线程池控制线程数量,其他线程排队等候。一个任务执行完毕,再从队列的中取最前面的任务开始执行。若队列中没有等待进程,线程池的这一资源处于等待。当一个新任务需要运行时,如果线程池中有等待的工作线程,就可以开始运行了;否则进入等待队列。 为什么要用线程池: 1.减少了创建和销毁线程的次数,每个工作线程都可以被重复利用,可执行多个任务。 2.可以根据系统的承受能力,调整线程池中工作线线程的数目,防止因为消耗过多的内存,而把服务器累趴下(每个线程需要大约1MB内存,线程开的越多,消耗的内存也就越大,最后死机)。 Java里面线程池的顶级接口是Executor,但是严格意义上讲Executor并不是一个线程池,而只是一个执行线程的工具

线程池原理之自定义线程池

谁说我不能喝 提交于 2019-12-02 19:43:00
一、 队列 先说一下线程池底层的数据结构 队列:一种线性表,它的特性是先进先出,插入在一端,删除在另一端。 队列又分为阻塞队列BlockingQueue和非阻塞队列ConcurrentLinkedQueue 生产者生产元素插入队列,消费者消费元素在另一端删除(假定队列的容量为10) 它们两者的区别: 1、非阻塞队列:如果存放超出队列容量,则 队列信息丢失; 阻塞队列:如果存放超出队列容量,则 进行等待 (等待时间为队列设置的生产者等待超时时间) 2、非阻塞队列:获取队列元素时,若队列为空,则 返回null ; 阻塞队列:获取队列元素时,若队列为空,则 进行等待 (等待时间为队列设置的消费者等待超时时间) 阻塞队列在操作中若规定了超时时间,但是操作不需要等待时,就不用等待;若在规定的超时时间内没有完成操作,则放弃操作。若不规定超时时间,就可以认为是非阻塞队列。 其中线程池底层使用的就是 阻塞队列 。 二、线程的状态 下面是大家熟知的线程状态转换图: 三、线程池 线程池简单来说就是管理线程的,使用它的优点有以下三个大的方面: 1、降低资源消耗: 重复利用机制 降低了线程创建、销毁的资源消耗; 2、提高相应效率:调度线程时状态切换较快; 3、方便管理 3.1 线程池创建的几种方式 四种线程池的创建方式,在底层使用的都是 ThreadPoolExecutor 的构造方法 1、可缓存线程池

自定义线程池

不羁岁月 提交于 2019-12-02 19:41:07
java开发经常使用到线程池,有一些concurent包里面提供的线程池 固定的,缓存的等等; 但是只有自己构建一个线程池才能了解到线程池的真正使用。 一、 threadPoolExecutor = new ThreadPoolExecutor( 2 , 2 , 1000 , TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>( 2 ), new ThreadPoolExecutor.CallerRunsPolicy()); 核心线程数:2 最多线程数:2 存储队列:LinkedBlockingQueue 大小为2 reject方法:Caller 执行逻辑是这样的 核心线程2满了就放到存储队列中去,存储队列满了,就开一个线程,直到达到最大线程数,再有线程进来就直接执行excutor方法执行,不放在线程池中执行 实际使用: 存储队列为2,是远远不能满足当前的线程数量的 所以开出了一个 main线程来执行过程 二、 threadPoolExecutor = new ThreadPoolExecutor( 2 , 2 , 1000 , TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>( 2 )); 相比上面那个,没有设置拒绝策略

java线程安全之Executor框架及自定义线程池(十五)

☆樱花仙子☆ 提交于 2019-12-02 19:40:55
Executor框架及自定义线程池 Executor框架 概念理解 为了更好的控制多线程,JDK提供了一套线程框架Executor,帮助开发人员有效地进行线程控制。它们都在Java.util.concurrent包中,是JDK并发包的核心。其中有一个比较重要的类:Executors,他扮演这线程工厂的角色,我们通过Executors可以创建特定功能的线程池。Executors创建线程池方法: newFixedThreadPool()方法,该方法返回一个固定数量的线程池,该方法的线程数始终不变,当有一个任务提交时,若线程池中空闲,则立即执行,若没有,则会被暫缓在一个任务队列中等待有空闲的线程去执行· 具体源码如下: public static ExecutorService newFixedThreadPool ( int nThreads) { return new ThreadPoolExecutor(nThreads, nThreads, //初始化多少个线程 / 最大线程 0 L, TimeUnit.MILLISECONDS, //这两个参数一起用的等待的时间 这里为 0 new LinkedBlockingQueue<Runnable>()); //无界队列 如果这个任务没有空闲线程就会 缓存到这个线程中 } newSingleThreadExecutor()方法

自定义线程池要点总结

我们两清 提交于 2019-12-02 19:40:26
自定义线程池的核心:ThreadPoolExecutor 为了更好的控制多线程,JDK提供了一套线程框架Executor,帮助开发人员有效的进行线程控制,其中在java.util.concurrent包下,是JDK并发包的核心,比如我们熟知的Executors。Executors扮演着线程工厂的角色,我们通过它可以创建特定功能的线程池,而这些线程池背后的就是:ThreadPoolExecutor。那么下面我们来具体分析下它。 构造ThreadPoolExecutor: public ThreadPoolExecutor(int corePoolSize, int maximumPoolSize, long keepAliveTime, TimeUnit unit, BlockingQueue<Runnable> workQueue, ThreadFactory threadFactory, RejectedExecutionHandler handler) { if (corePoolSize < 0 || maximumPoolSize <= 0 || maximumPoolSize < corePoolSize || keepAliveTime < 0) throw new IllegalArgumentException(); if (workQueue == null ||

java ThreadPoolExecutor 自定义线程池优势

半腔热情 提交于 2019-12-02 19:40:16
java并发线程池建议还是多多使用ThreadPoolExecutor的构造函数来设置自定义的线程池,先来看看这个构造函数的参数列表。 /** * Creates a new {@code ThreadPoolExecutor} with the given initial * parameters. * * @param corePoolSize the number of threads to keep in the pool, even * if they are idle, unless {@code allowCoreThreadTimeOut} is set * @param maximumPoolSize the maximum number of threads to allow in the * pool * @param keepAliveTime when the number of threads is greater than * the core, this is the maximum time that excess idle threads * will wait for new tasks before terminating. * @param unit the time unit for the {@code keepAliveTime}

使用Executor框架创建线程池+自定义线程池+JDK拒绝策略

自古美人都是妖i 提交于 2019-12-02 19:32:39
Executors创建线程池 为了更好的控制多线程,JDK提供了一套线程框架Executor,帮助开发人员有效地进行线程控制。它们都在java.util.concurrent包中,是JDK并发包的核心。其中有一个比较重要的类:Executors,它扮演着线程工厂的角色,我们通过Executors可以创建特定功能的线程池。 Executors创建线程池方法: newFixedThreadPool()方法,该方法返回一个固定数量的线程池,该方法的线程数始终不变,当有一个任务提交时,若线程池中空闲,则立即执行,若没有,则会被暂时缓存在一个任务队列中,等待有空闲的线程去执行。 newSingleThreadExecutor()方法,创建一个线程的线程池,若空闲则执行,若没有空闲线程则暂缓在任务队列中。 newCachedThreadPool()方法,返回一个可以根据实际情况调整线程个数的线程池,不限制最大线程数量。只要有一个任务来了,就创建一个线程去执行任务。若无任务则不创建线程。并且每一个空闲线程会在60秒后自动回收。 newScheduledThreadPool()方法,该方法返回一个ScheduledExecutorService对象。但该线程池可以指定线程的数量,其中的每一个线程可以实现定时器的作用。 无论创建哪种类型的线程池