博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
ScheduledThreadPoolExecutor类的使用
阅读量:3959 次
发布时间:2019-05-24

本文共 7773 字,大约阅读时间需要 25 分钟。

系列文章目录

关系图:

在这里插入图片描述

文章目录


前言

ScheduledThreadPoolExecutor它与ThreadPoolExecutor最大的不同就是可以设置延迟任务和中期任务。

0.熟悉api

构造方法:

ScheduledThreadPoolExecutor(int corePoolSize)           指定核心线程大小,最大线程数默认为Integer.MAX_VALUE ScheduledThreadPoolExecutor(int corePoolSize, RejectedExecutionHandler handler)           指定核心线程大小,最大线程数默认为Integer.MAX_VALUE并指定饱和策略ScheduledThreadPoolExecutor(int corePoolSize, ThreadFactory threadFactory)               指定核心线程大小,最大线程数默认为Integer.MAX_VALUE并指定线程工厂 ScheduledThreadPoolExecutor(int corePoolSize, ThreadFactory threadFactory, RejectedExecutionHandler handler)               指定核心线程大小,最大线程数默认为Integer.MAX_VALUE并指定饱和策略和线程工厂

常用方法:

1.schedule方法

该方法可以用来延迟任务的执行

延迟执行任务一次:public ScheduledFuture
schedule( Runnable command, long delay, TimeUnit unit) 参数:command:执行的任务delay:延迟的时间unit:枚举类,表示时间的单位可以是时分秒……

案例:

public class ScheduleThreadPoolExecutorTest {
public static void main(String[] args) {
System.out.println("当前系统时间"+System.currentTimeMillis()); //使用该构造方法默认最大核心线程数为Interger_Max ScheduledThreadPoolExecutor executor = new ScheduledThreadPoolExecutor(5); executor.schedule(new Runnable() {
@Override public void run() {
System.out.println("开始执行时间"+System.currentTimeMillis()); } },2, TimeUnit.SECONDS); //延迟两秒再执行 executor.shutdown(); }}

在这里插入图片描述

运行该程序时,你会发现先打印了当前系统时间,过了两秒后才打印出开始执行


2.固定频率执行任务

scheduleAtFixedRate()方法

public ScheduledFuture
scheduleAtFixedRate(Runnable command, long initialDelay, long period, TimeUnit unit);参数:command:执行的任务initialDelay:首次执行的延迟时间period:表示每次间隔的时间unit:枚举类是上述两个时间的单位

案例:

import java.sql.SQLOutput;import java.text.SimpleDateFormat;import java.util.Date;import java.util.concurrent.Executors;import java.util.concurrent.ScheduledThreadPoolExecutor;import java.util.concurrent.TimeUnit;public class ScheduleThreadPoolExecutorTest {
public static void main(String[] args) {
System.out.println("2秒后开始打印当前时间"+getNowTime(System.currentTimeMillis())); ScheduledThreadPoolExecutor executor = new ScheduledThreadPoolExecutor(100); executor.scheduleAtFixedRate(new Runnable() {
@Override public void run() {
System.out.println("当前时间"+getNowTime(System.currentTimeMillis())); try {
//这里休眠是为了和后续的方法做比较 Thread.sleep(1000); } catch (InterruptedException e) {
e.printStackTrace(); } } },2,1,TimeUnit.SECONDS); } public static String getNowTime(Long time){
return new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(time); }}

打印结果:

在这里插入图片描述

3.固定的间隔时间执行任务

scheduleWithFixedDelay

public ScheduledFuture
scheduleWithFixedDelay(Runnable command, long initialDelay, long period, TimeUnit unit);参数:command:执行的任务initialDelay:首次执行的延迟时间period:表示每次间隔的时间unit:枚举类是上述两个时间的单位

代码如下(示例):

import java.sql.SQLOutput;import java.text.SimpleDateFormat;import java.util.Date;import java.util.concurrent.Executors;import java.util.concurrent.ScheduledThreadPoolExecutor;import java.util.concurrent.TimeUnit;public class ScheduleThreadPoolExecutorTest {
public static void main(String[] args) {
System.out.println("2秒后开始打印当前时间"+getNowTime(System.currentTimeMillis())); ScheduledThreadPoolExecutor executor = new ScheduledThreadPoolExecutor(100); executor.scheduleWithFixedDelay(new Runnable() {
@Override public void run() {
System.out.println("当前时间"+getNowTime(System.currentTimeMillis())); try {
Thread.sleep(1000); } catch (InterruptedException e) {
e.printStackTrace(); } } },2,1,TimeUnit.SECONDS); } public static String getNowTime(Long time){
return new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(time); }}

在这里插入图片描述

scheduleAtFixedRate和scheduleWithFixedDelay两者的区别

scheduleAtFixedRate的下一次执行时间是上一次执行时间+间隔时间

scheduleWithFixedDelay下一次执行时间是上一次执行时间结束时系统时间+间隔时间。
scheduleWithFixedDelay时间不固定但是周期固定

所以第一个案例下一次执行时间间隔了1秒,而第二个案例中每一次任务内部执行了1秒,所以下一次的执行时间就是2秒。

4.定时任务出现异常

如果说scheduleAtFixedRate和scheduleWithFixedDelay在执行时出现异常会怎么样?

案例:

import java.sql.SQLOutput;import java.text.SimpleDateFormat;import java.util.Date;import java.util.concurrent.Executors;import java.util.concurrent.ScheduledFuture;import java.util.concurrent.ScheduledThreadPoolExecutor;import java.util.concurrent.TimeUnit;public class ScheduleThreadPoolExecutorTest {
public static void main(String[] args) {
System.out.println("2秒后开始打印当前时间"+getNowTime(System.currentTimeMillis())); ScheduledThreadPoolExecutor executor = new ScheduledThreadPoolExecutor(100); ScheduledFuture
scheduledFuture = executor.scheduleWithFixedDelay(new Runnable() {
@Override public void run() {
System.out.println("当前时间" + getNowTime(System.currentTimeMillis())); try {
Thread.sleep(1000); //制造异常 int i = 2 / 0; } catch (InterruptedException e) {
e.printStackTrace(); } } }, 2, 1, TimeUnit.SECONDS); } public static String getNowTime(Long time){
return new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(time); }}

我们手动只要了一个异常:看一下结果

在这里插入图片描述
程序执行到异常的时候不在执行了。

当我们在使用ScheduledExecutorService接口的实现类处理任务的时候,如果一旦发生异常,就会被ScheduledExecutorService接口内部进行捕获。因此我们在发现程序不正确的时候需要即时查找原因。不然程序停止了也没有异常信息的打印。

5.取消定时任务的执行

我们在使用ScheduleThreadPoolExecutor执行任务时都会返回ScheduledFuture的。我们可以通过方法进行发送中断信号来取消定时任务

boolean cancel(boolean mayInterruptIfRunning)           试图取消对此任务的执行。   boolean isCancelled()           如果在任务正常完成前将其取消,则返回 true。  boolean isDone()           如果任务已完成,则返回 true。

案例:

5秒后取消定时任务:

import java.sql.SQLOutput;import java.text.SimpleDateFormat;import java.util.Date;import java.util.concurrent.Executors;import java.util.concurrent.ScheduledFuture;import java.util.concurrent.ScheduledThreadPoolExecutor;import java.util.concurrent.TimeUnit;public class ScheduleThreadPoolExecutorTest {
public static void main(String[] args) {
System.out.println("2秒后开始打印当前时间"+getNowTime(System.currentTimeMillis())); ScheduledThreadPoolExecutor executor = new ScheduledThreadPoolExecutor(100); ScheduledFuture
scheduledFuture = executor.scheduleAtFixedRate(new Runnable() {
@Override public void run() {
System.out.println("当前时间" + getNowTime(System.currentTimeMillis())); try {
Thread.sleep(1000); } catch (InterruptedException e) {
e.printStackTrace(); } } }, 2, 1, TimeUnit.SECONDS); try {
Thread.sleep(5000); //取消定时任务 scheduledFuture.cancel(true); if(scheduledFuture.isDone()){
System.out.println("任务完成"); } if(scheduledFuture.isCancelled()){
System.out.println("任务取消"); } } catch (InterruptedException e) {
e.printStackTrace(); } } public static String getNowTime(Long time){
return new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(time); }}

结果:

在这里插入图片描述

转载地址:http://znxzi.baihongyu.com/

你可能感兴趣的文章