执行一个异步任务你还只是以下new Thread吗?java
new Thread(new Runnable() {
@Override
public void run() {
// TODO Auto-generated method stub
}
}).start();
复制代码
new Thread的弊端以下:数据库
Java经过Executors提供四种线程池,分别为:缓存
Executors 主要是这个构造函数:安全
public ThreadPoolExecutor(int corePoolSize, int maximumPoolSize, long keepAliveTime, TimeUnit unit, BlockingQueue<Runnable> workQueue, ThreadFactory threadFactory, RejectedExecutionHandler handler) 复制代码
而Executors工厂类一共能够建立四种类型的线程池,经过Executors.newXXX便可建立。下面就分别都介绍一下把。网络
建立一个定长线程池,可控制线程最大并发数,超出的线程会在队列中等待。示例代码以下:并发
ExecutorService fixedThreadPool = Executors.newFixedThreadPool(3);
for (int i = 0; i < 10; i++) {
final int index = i;
fixedThreadPool.execute(new Runnable() {
@Override
public void run() {
try {
System.out.println(index);
Thread.sleep(2000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
});
}
复制代码
由于线程池大小为3,每一个任务输出index后sleep 2秒,因此每两秒打印3个数字。异步
定长线程池的大小最好根据系统资源进行设置。ide
public static ExecutorService newFixedThreadPool(int nThreads){
return new ThreadPoolExecutor(nThreads,nThreads,0L,TimeUnit.MILLISECONDS,new LinkedBlockingQueue<Runnable>());
}
复制代码
建立一个可缓存线程池,若是线程池长度超过处理须要,可灵活回收空闲线程,若无可回收,则新建线程。示例代码以下:函数
ExecutorService cachedThreadPool = Executors.newCachedThreadPool();
for (int i = 0; i < 10; i++) {
final int index = i;
try {
Thread.sleep(index * 1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
cachedThreadPool.execute(new Runnable() {
@Override
public void run() {
System.out.println(index);
}
});
}
复制代码
//构造函数
public static ExecutorService newCachedThreadPool(){
return new ThreadPoolExecutor(0,Integer.MAX_VALUE,60L,TimeUnit.MILLISECONDS,new SynchronousQueue<Runnable>());
}
复制代码
线程池为无限大,当执行第二个任务时第一个任务已经完成,会复用执行第一个任务的线程,而不用每次新建线程。性能
建立一个单线程化的线程池,它只会用惟一的工做线程来执行任务,保证全部任务按照指定顺序(FIFO, LIFO, 优先级)执行。示例代码以下:
ExecutorService singleThreadExecutor = Executors.newSingleThreadExecutor();
for (int i = 0; i < 10; i++) {
final int index = i;
singleThreadExecutor.execute(new Runnable() {
@Override
public void run() {
try {
System.out.println(index);
Thread.sleep(2000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
});
}
复制代码
结果依次输出,至关于顺序执行各个任务。
public static ExecutorService newSingleThreadExecutor(){
return new ThreadPoolExecutor(1,1,0L,TimeUnit.MILLISECONDS,new LinkedBlockingQueue<Runnable>());
}
复制代码
它只会建立一条工做线程处理任务;采用的阻塞队列为LinkedBlockingQueue;
建立一个定长线程池,支持定时及周期性任务执行。延迟执行示例代码以下:
ScheduledExecutorService scheduledThreadPool = Executors.newScheduledThreadPool(5);
scheduledThreadPool.schedule(new Runnable() {
@Override
public void run() {
System.out.println("delay 3 seconds");
}
}, 3, TimeUnit.SECONDS);
复制代码
表示延迟3秒执行。
scheduledThreadPool.scheduleAtFixedRate(new Runnable() {
@Override
public void run() {
System.out.println("delay 1 seconds, and excute every 3 seconds");
}
}, 1, 3, TimeUnit.SECONDS);
复制代码
表示延迟1秒后每3秒执行一次。
ScheduledExecutorService比Timer更安全,功能更强大
DelayQueue内部封装了一个PriorityQueue,它会根据time的前后时间排序,若time相同则根据sequenceNumber排序;
DelayQueue也是一个无界队列;
工做线程会从DelayQueue取已经到期的任务去执行;
执行结束后从新设置任务的到期时间,再次放回DelayQueue
默认是一个CachedThreadScheduler,用于IO密集型任务,如异步阻塞IO操做(读写文件、读写数据库、网络信息交互等)所使用的 Scheduler。
默认是:FixedThreadPool。用于CPU 密集型计算,即不会被 I/O 等操做限制性能的操做,例如图形的计算,事件循环或和回调处理
在当前线程当即开始执行任务,至关于不指定线程。这是默认的 Scheduler
Android专用的,指定的操做将在 Android 主线程运行
使用指定的Executor做为调度器
老是启用新线程,并在新线程执行操做。
executor = new ThreadPoolExecutor(0, 2147483647, 60L, TimeUnit.SECONDS, new SynchronousQueue(), Util.threadFactory("OkHttp ConnectionPool", true));
复制代码