转:java中的定时任务
引自:http://www.cnblogs.com/wenbronk/p/6433178.html
java中的定时任务, 使用java实现有3种方式:
1, 使用普通thread实现
@Test
public void test1() {
// 单位: 毫秒
final long timeInterval = 1000;
Runnable runnable = new Runnable() {
public void run() {
while (true) {
// ------- code for task to run
System.out.println("Hello !!");
// ------- ends here
try {
Thread.sleep(timeInterval);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
};
Thread thread = new Thread(runnable);
thread.start();
}
2, 使用timer实现: 可控制启动或取消任务, 可指定第一次执行的延迟
线程安全, 但只会单线程执行, 如果执行时间过长, 就错过下次任务了, 抛出异常时, timerWork会终止
@Test
public void test2 () {
TimerTask task = new TimerTask() {
@Override
public void run() {
System.out.println("Hello !!!");
}
};
Timer timer = new Timer();
long delay = 0;
long intevalPeriod = 1 * 1000;
// schedules the task to be run in an interval
timer.scheduleAtFixedRate(task, delay, intevalPeriod);
}
3, 使用 ScheduledExcecutorService 实现
ScheduledExecutorService 是java.util.concurrent种的额一个累, 用于实现定时任务
它可以: 1, 通过线程池的方式执行任务
2, 设定第一次的延迟事件
3, 提供良好的约定, 设定时间间隔
@Test
public void test() {
Runnable runnable = new Runnable() {
public void run() {
System.out.println("Hello !!");
}
};
ScheduledExecutorService service = Executors
.newSingleThreadScheduledExecutor();
// 第二个参数为首次执行的延时时间,第三个参数为定时执行的间隔时间
service.scheduleAtFixedRate(runnable, 10, 1, TimeUnit.SECONDS);
}
4, 使用spring的 spring-task 实现
第一种方式, 注解的方式实现
@Target({java.lang.annotation.ElementType.METHOD, java.lang.annotation.ElementType.ANNOTATION_TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Scheduled
{
public abstract String cron();
public abstract long fixedDelay();
public abstract long fixedRate();
}
fixedDelay: 设定间隔时间为 5000ms
fixedRate: 设定固定速率, 以固定速率5s来执行
cron="0 0 2 * * ? ": 使用时间表达式
第二种方式, 配置文件配置的方式实现
<task:scheduled-tasks>
<task:scheduled ref="taskJob" method="job1" cron="0 * * * * ?"/>
</task:scheduled-tasks>
/* taskJob 为执行任务类, job1 为执行的函数*/
<context:component-scan base-package="com.wenbronk.mytask " />
2, 添加配置信息
<!—开启这个配置,spring才能识别@Scheduled注解 -->
<task:annotation-driven scheduler="qbScheduler" mode="proxy"/>
<task:scheduler id="qbScheduler" pool-size="10"/>
3, 代码实现
@Scheduled(fixedDelay = 5000)
public void doSomething() {
// something that should execute periodically
}
时间表达式
一个cron表达式有至少6个(也可能7个)有空格分隔的时间元素。
按顺序依次为
秒(0~59)
分钟(0~59)
小时(0~23)
天(月)(0~31,但是你需要考虑你月的天数)
月(0~11)
天(星期)(1~7 1=SUN 或 SUN,MON,TUE,WED,THU,FRI,SAT)
年份(1970-2099)
常用的表达式为:
0 0 10,14,16 * * ? 每天上午10点,下午2点,4点
0 0/30 9-17 * * ? 朝九晚五工作时间内每半小时
0 0 12 ? * WED 表示每个星期三中午12点
"0 0 12 * * ?" 每天中午12点触发
"0 15 10 ? * *" 每天上午10:15触发
"0 15 10 * * ?" 每天上午10:15触发
"0 15 10 * * ? *" 每天上午10:15触发
"0 15 10 * * ? 2005" 2005年的每天上午10:15触发
"0 * 14 * * ?" 在每天下午2点到下午2:59期间的每1分钟触发
"0 0/5 14 * * ?" 在每天下午2点到下午2:55期间的每5分钟触发
"0 0/5 14,18 * * ?" 在每天下午2点到2:55期间和下午6点到6:55期间的每5分钟触发
"0 0-5 14 * * ?" 在每天下午2点到下午2:05期间的每1分钟触发
"0 10,44 14 ? 3 WED" 每年三月的星期三的下午2:10和2:44触发
"0 15 10 ? * MON-FRI" 周一至周五的上午10:15触发
"0 15 10 15 * ?" 每月15日上午10:15触发
"0 15 10 L * ?" 每月最后一日的上午10:15触发
"0 15 10 ? * 6L" 每月的最后一个星期五上午10:15触发
"0 15 10 ? * 6L 2002-2005" 2002年至2005年的每月的最后一个星期五上午10:15触发
"0 15 10 ? * 6#3" 每月的第三个星期五上午10:15触发
5, 使用 第三方插件 Quartz实现
maven依赖
<dependency>
<groupId>org.quartz-scheduler</groupId>
<artifactId>quartz</artifactId>
<version>2.2.1</version>
</dependency>
5. 1) 可以设置一个类, 继承自 QuartzJobBean
1, 配置文件:
<!-- 配置作业类 -->
<bean name="job1" class="org.springframework.scheduling.quartz.JobDetailBean">
<property name="jobClass" value="com.gy.Job1" />
<property name="jobDataAsMap">
<map>
<entry key="timeout" value="0" />
</map>
</property>
</bean> <!-- 配置触发方式 -->
<!-- simpleTrggerBean 只支持一种方式调度 -->
<bean id="simpleTrigger" class="org.springframework.scheduling.quartz.SimpleTriggerBean">
<property name="jobDetail" ref="job1" />
<property name="startDelay" value="0" /> <!-- 调度工厂实例化后,经过0秒开始执行调度 -->
<property name="repeatInterval" value="2000" /> <!-- 每2秒调度一次 -->
</bean> <!-- 使用CronTrggerBean , 支持时间表达式 -->
<bean id="cronTrigger" class="org.springframework.scheduling.quartz.CronTriggerBean">
<property name="jobDetail" ref="job1" />
<!-- 每天12点运行一次 -->
<property name="cronExpression" value="0 0 12 * * ?" />
</bean>
2, 配置调度工厂:
<bean class="org.springframework.scheduling.quartz.SchedulerFactoryBean">
<property name="triggers">
<list>
<ref bean="cronTrigger" />
</list>
</property>
</bean>
3, 定义作业类:
public class Job1 extends QuartzJobBean {
private int timeout;
private static int i = 0;
// 调度工厂实例化后,经过timeout时间开始执行调度
public void setTimeout(int timeout) {
this.timeout = timeout;
}
/**
* 要调度的具体任务
*/
@Override
protected void executeInternal(JobExecutionContext context) throws JobExecutionException {
System.out.println("定时任务执行中…");
}
}
5.2) 直接写一个普通类, 在配置中进行配置
任务类:
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.StringRedisTemplate; /**
* 定时删除用户收听过的poi
* @author wenbronk
* @time 2017年3月28日 下午2:01:09 2017
*/
public class DelListenerPOIScheduler { @Autowired
private StringRedisTemplate redisTemplate; public void doCheck() {
System.out.println("定时任务执行了....");
} }
配置文件:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:mvc="http://www.springframework.org/schema/mvc" xmlns:tx="http://www.springframework.org/schema/tx"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-4.2.xsd
http://www.springframework.org/schema/tx
http://www.springframework.org/schema/tx/spring-tx-4.2.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop-4.2.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop-4.2.xsd
http://www.springframework.org/schema/mvc
http://www.springframework.org/schema/mvc/spring-mvc-4.2.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-4.2.xsd"> <!-- 配置作业类 -->
<bean id="delRedisListenerHistory" class="com.iwhere.easy.travel.valid.DelListenerPOIScheduler" /> <!-- 作业类描述, 使用方法调度 -->
<bean id="methodInvoking"
class="org.springframework.scheduling.quartz.MethodInvokingJobDetailFactoryBean">
<property name="targetObject" ref="delRedisListenerHistory" />
<property name="targetMethod" value="doCheck" />
</bean> <!-- 触发器, 使用定时触发 -->
<bean id="delTrigger"
class="org.springframework.scheduling.quartz.CronTriggerFactoryBean">
<property name="jobDetail" ref="methodInvoking" />
<property name="cronExpression" value="0/10 * * * * ?" />
</bean> <!-- 总调度器 -->
<bean class="org.springframework.scheduling.quartz.SchedulerFactoryBean">
<property name="triggers">
<list>
<ref bean="delTrigger" />
</list>
</property>
</bean> </beans>
6, 在springboot中实现定时任务:
package com.iwhere.base.scheduling; import org.springframework.context.annotation.Configuration;
import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.scheduling.annotation.Scheduled; /**
* 整合定时任务
* EnableScheduling 实现spring中的task功能
* @Scheduled中配置时间表达式
* @author 231
*
*/
@Configuration // 相当于配置beans,
@EnableScheduling // <task:*>, 让spring进行任务调度
public class SchedulingConfig { @Scheduled(cron="0/20 * * * * ?") // 20秒执行一次
public void scheduler() {
System.out.println("定时任务执行了");
} }
7, Springboot 集成 quartz
为什么非要集成呢, 因为quartz支持集群定时任务, 现在还用不到, 防止以后用到
1, 配置quartz的配置信息类
package com.iwhere.easy.travel.timeschedule; import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.scheduling.quartz.CronTriggerFactoryBean;
import org.springframework.scheduling.quartz.MethodInvokingJobDetailFactoryBean;
import org.springframework.scheduling.quartz.SchedulerFactoryBean;
/**
* quartz的配置信息
* @author wenbronk
* @time 2017年3月29日 下午5:20:29 2017
*/
@Configuration
public class TimeScheduleConfig { @Bean(name = "detailFactoryBean")
public MethodInvokingJobDetailFactoryBean detailFactoryBean(DelListenerPOIScheduler scheduledTasks) {
MethodInvokingJobDetailFactoryBean bean = new MethodInvokingJobDetailFactoryBean();
// 这儿设置对应的Job对象
bean.setTargetObject(scheduledTasks);
// 这儿设置对应的方法名 与执行具体任务调度类中的方法名对应
bean.setTargetMethod("doCheck");
bean.setConcurrent(false);
return bean;
} @Bean(name = "cronTriggerBean")
public CronTriggerFactoryBean cronTriggerBean(MethodInvokingJobDetailFactoryBean detailFactoryBean) {
CronTriggerFactoryBean trigger = new CronTriggerFactoryBean();
trigger.setJobDetail(detailFactoryBean.getObject());
try {
trigger.setCronExpression("0 0 1 * * ?");// 每天1点执行一次
} catch (Exception e) {
e.printStackTrace();
}
return trigger; } @Bean
public SchedulerFactoryBean schedulerFactory(CronTriggerFactoryBean cronTriggerBean) {
SchedulerFactoryBean schedulerFactory = new SchedulerFactoryBean();
schedulerFactory.setTriggers(cronTriggerBean.getObject());
return schedulerFactory;
} }
2), 具体的作业类
package com.iwhere.easy.travel.timeschedule; import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Configurable;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.stereotype.Component; /**
* 定时删除用户收听过的poi
* @author wenbronk
* @time 2017年3月28日 下午2:01:09 2017
*/
@Component
@Configurable
@EnableScheduling
public class DelListenerPOIScheduler {
private Logger LOGGER = LoggerFactory.getLogger(DelListenerPOIScheduler.class); @Autowired
private StringRedisTemplate redisTemplate; public void doCheck() { try {
String key = "noteUserListenedPoi:*";
redisTemplate.delete(key);
LOGGER.info("redis中用户收听历史被清空");
} catch (Exception e) {
e.printStackTrace();
LOGGER.error("redis删除用户收听记录失败");
}
} }
系列原创, 转载请注明出处, 谢谢 @Wenbronk: http://www.cnblogs.com/wenbronk/p/6433178.html
转:java中的定时任务的更多相关文章
- Java 中的定时任务(一)
定时任务简单来说就是在指定时间,指定的频率来执行一个方法,而在 Java 中我们又该如何实现呢? 想来主要有 3 种方式,最原始的方式肯定是开启一个线程,让它睡一会跑一次睡一会跑一次这也就达到了定频率 ...
- Java中的定时任务
现代的应用程序早已不是以前的那些由简单的增删改查拼凑而成的程序了,高复杂性早已是标配,而任务的定时调度与执行也是对程序的基本要求了. 很多业务需求的实现都离不开定时任务,例如,每月一号,移动将清空你上 ...
- java中实现定时任务 task 或quartz
转载大神的 https://www.cnblogs.com/hafiz/p/6159106.html https://www.cnblogs.com/luchangyou/p/6856725.html ...
- java中的定时任务小示例
package package_1; import java.text.SimpleDateFormat; import java.util.Date; import java.util.Timer; ...
- java中实现定时功能
网上资料: 我们可以使用Timer和TimerTask类在java中实现定时任务,详细说明如下: 1.基础知识java.util.Timer一种线程设施,用于安排以后在后台线程中执行的任务.可安排任务 ...
- java中基于TaskEngine类封装实现定时任务
主要包括如下几个类: 文章标题:java中基于TaskEngine类封装实现定时任务 文章地址: http://blog.csdn.net/5iasp/article/details/10950529 ...
- 在Java Web项目中添加定时任务
在Java Web程序中加入定时任务,这里介绍两种方式:1.使用监听器注入:2.使用Spring注解@Scheduled注入. 推荐使用第二种形式. 一.使用监听器注入 ①:创建监听器类: impor ...
- 如何用 Java 实现 Web 应用中的定时任务?
定时任务,是指定一个未来的时间范围执行一定任务的功能.在当前WEB应用中,多数应用都具备任务调度功能,针对不同的语音,不同的操作系统, 都有其自己的语法及解决方案,windows操作系统把它叫做任务计 ...
- 如何用 Java 实现 Web 应用中的定时任务
定时任务,是指定一个未来的时间范围执行一定任务的功能.在当前WEB应用中,多数应用都具备任务调度功能,针对不同的语音,不同的操作系统, 都有其自己的语法及解决方案,windows操作系统把它叫做任务计 ...
随机推荐
- BZOJ4010: [HNOI2015]菜肴制作(拓扑排序 贪心)
题意 题目链接 Sol 震惊,HNOI竟出NOI原题 直接在反图上贪心一下. // luogu-judger-enable-o2 // luogu-judger-enable-o2 #include& ...
- 【Linux】应用程序内存段布局
一.各段内存布局 内存布局图 1.BSS段(Block Started by Symbol)未初始化段 2.linux ELF base address is 0x8048000 应用程序虚拟地址起始 ...
- linux搭建nginx图片服务器
1:参考http://blog.csdn.net/u012401711/article/details/53525908
- Struts1.x 中处理乱码及通过标签显示数据
1.通过filter解决乱码问题 网页的请求到达之前,先要经过filter的处理: 提取数据出现乱码:request.setCharacterEncoding("UTF-8"); ...
- selenium(2.4.0)中不能导出web drive 代码
最近在学习selenium.要做web自动化测试.咱只会C# .就想了,这个测试用例要是能用C# 控制,保存起来,就可以以后自动运行了,不用每次点击运行了. 看了看它的文档,就开始试验了,录脚本折腾了 ...
- css:改变滚动条样式
以下亲测谷歌内核的浏览器有用,微软和火狐无效 body::-webkit-scrollbar {/*滚动条整体样式*/ width: 5px; /*高宽分别对应横竖滚动条的尺寸*/ height: 1 ...
- 把IDENTITY_INSERT 设置为 ON ,还不能插入数据问题
IDENTITY_INSERT 为 ON 时 , 必须把需要插入的列名列出来 不然报错 正确例子: SET IDENTITY_INSERT table(表名) ONinsert into table ...
- jquery-tags-input 使用经历
源代码里有这么一段,是在tagsInput这里,第一次初始化的时候是正常的,但当第二次初始化的时候就会出现问题,id的值会组合为 id+new Date().getTime() 暂时不清楚作用是什么 ...
- 我的HTML总结之HTML发展史
HTML是Web统一语言,这些容纳在尖括号里的简单标签,构成了如今的Web. 1991年,Tim Berners-Lee编写了一份叫做“HTML标签”的文档,里面包含了大约20个用来标记网页的HTML ...
- 【转载】#438 - Benefits of Using Interfaces
You might wonder why you'd define an interface, have a class implement that interface and then acces ...