在应用里经常都有用到在后台跑定时任务的需求。举个例子,比如需要在服务后台跑一个定时任务来进行垃圾回收(译者注:个人觉得用定时任务来跑垃圾回收不是很好的例子,从译者接触到的项目来看,比较常见的是用定时任务来进行非实时计算,清除临时数据、文件等)。
在本文里,我会给大家介绍3种不同的实现方法:
普通thread实现 TimerTask实现 ScheduledExecutorService实现
普通thread
这是最常见的,创建一个thread,然后让它在while循环里一直运行着,通过sleep方法来达到定时任务的效果。这样可以快速简单的实现,代码如下:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
public
class
Task1
{
public
static
void
main
(
String
[
]
args
)
{
// run in a second
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
(
)
;
}
}
用Timer和TimerTask
上面的实现是非常快速简便的,但它也缺少一些功能。 用Timer和TimerTask的话与上述方法相比有如下好处:
当启动和去取消任务时可以控制 第一次执行任务时可以指定你想要的delay时间
在实现时,Timer类可以调度任务,TimerTask则是通过在run()方法里实现具体任务。 Timer实例可以调度多任务,它是线程安全的。 当Timer的构造器被调用时,它创建了一个线程,这个线程可以用来调度任务。 下面是代码:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
import
java
.
util
.
Timer
;
import
java
.
util
.
TimerTask
;
public
class
Task2
{
public
static
void
main
(
String
[
]
args
)
{
TimerTask
task
=
new
TimerTask
(
)
{
@
Override
public
void
run
(
)
{
// task to run goes here
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
)
;
}
// end of main
}
这些类从JDK 1.3开始存在。
ScheduledExecutorService
ScheduledExecutorService是从Java SE 5的java.util.concurrent里,做为并发工具类被引进的,这是最理想的定时任务实现方式。 相比于上两个方法,它有以下好处:
相比于Timer的单线程,它是通过线程池的方式来执行任务的 可以很灵活的去设定第一次执行任务delay时间 提供了良好的约定,以便设定执行的时间间隔
下面是实现代码,我们通过ScheduledExecutorService#scheduleAtFixedRate展示这个例子,通过代码里参数的控制,首次执行加了delay时间。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
import
java
.
util
.
concurrent
.
Executors
;
import
java
.
util
.
concurrent
.
ScheduledExecutorService
;
import
java
.
util
.
concurrent
.
TimeUnit
;
public
class
Task3
{
public
static
void
main
(
String
[
]
args
)
{
Runnable
runnable
=
new
Runnable
(
)
{
public
void
run
(
)
{
// task to run goes here
System
.
out
.
println
(
"Hello !!"
)
;
}
}
;
ScheduledExecutorService
service
=
Executors
.
newSingleThreadScheduledExecutor
(
)
;
service
.
scheduleAtFixedRate
(
runnable
,
0
,
1
,
TimeUnit
.
SECONDS
)
;
}
}
英文原文在这。
文章地址: http://www.newhottopic.com/2014/04/09/how-schedule-task-run-interval/
You could use standard stuff from java.util.concurrent
:
import java.util.concurrent._
val ex = new ScheduledThreadPoolExecutor(1)
val task = new Runnable {
def run() = println("Beep!")
}
val f = ex.scheduleAtFixedRate(task, 1, 1, TimeUnit.SECONDS)
f.cancel(false)
Or java.util.Timer
:
val t = new java.util.Timer()
val task = new java.util.TimerTask {
def run() = println("Beep!")
}
t.schedule(task, 1000L, 1000L)
task.cancel()