how to calculate initialDelay for ScheduledExecutorService#scheduleAtFixedRate - java

I want to run a task at a specific time say at 7.11pm everyday.
I have tried the following piece of code but it is not working.
import java.util.Calendar;
import java.util.Date;
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() {
System.out.println(new Date());
System.out.println("Hello !!");
}
};
Calendar calendar = Calendar.getInstance();
long now = calendar.getTimeInMillis();
calendar.set(Calendar.HOUR, 18);
calendar.set(Calendar.MINUTE, 11);
calendar.set(Calendar.SECOND, 0);
calendar.set(Calendar.MILLISECOND, 0);
ScheduledExecutorService service = Executors.newSingleThreadScheduledExecutor();
service.scheduleAtFixedRate(runnable, calendar.getTimeInMillis(), 5, TimeUnit.SECONDS);
}
}
In the above code, I have tried to run the schedule task starting from 7:11pm everyday with an interval of 5 seconds. But it is not behaving as I expected to be. And also If I want to do the same with another condition that the task should be executed only on specific days let's say every Tuesday and Wednesday.
Am I making some kind of mistake in calculating the initialDelay parameter of the method or something else?

Side comment: it would probably be simpler to use an ad hoc library (such as quartz).
The initialDelay parameter gives the number of time unit to wait before running the task. In your case, you need to calculate the time left to 7:11.
So it could look like:
long nextRun = calendar.getTimeInMillis();
long initialDelayMillis = nextRun - now;
long oneDayMillis = 1000L * 60 * 60 * 24;
service.scheduleAtFixedRate(runnable, initialDelayMillis, oneDayMillis, TimeUnit.MILLISECONDS);
but this will only handle basic situations. In particular it won't handle clock adjustments or DST at all. And it won't be easy to say "only on Tuesdays and Wendesdays".
An alternative would be to only schedule the next run and reschedule it at the end of the runnable. That way you can have a finer control on the execution. But bottom line is: see my initial comment.

Preferable would be the scheduledExecutorService.
But maybe timer could be used too. For swing the other timer.
Here an example (the timer and timerTask could be stoped with cancel/purge).
import java.util.Calendar;
import java.util.Date;
import java.util.Timer;
import java.util.TimerTask;
public class TimeScheduleTest {
Timer timer = new Timer();
public static void main(String[] args) {
new TimeScheduleTest().startApp();
}
private void startApp() {
Calendar calendar = Calendar.getInstance();
calendar.set(Calendar.DAY_OF_WEEK,Calendar.TUESDAY);
calendar.set(Calendar.HOUR_OF_DAY, 7);
calendar.set(Calendar.MINUTE, 11);
calendar.set(Calendar.SECOND, 0);
calendar.set(Calendar.MILLISECOND, 0);
timer.scheduleAtFixedRate(new StartTimer(), calendar.getTime(), 5000);
}
class StartTimer extends TimerTask {
public void run() {
System.out.println(new Date());
System.out.println("Hello !!");
}
}
}

Related

How to read Spring Boot api every minute [duplicate]

I need to schedule a task to run in at fixed interval of time. How can I do this with support of long intervals (for example on each 8 hours)?
I'm currently using java.util.Timer.scheduleAtFixedRate. Does java.util.Timer.scheduleAtFixedRate support long time intervals?
Use a ScheduledExecutorService:
private final ScheduledExecutorService scheduler = Executors.newScheduledThreadPool(1);
scheduler.scheduleAtFixedRate(yourRunnable, 8, 8, TimeUnit.HOURS);
You should take a look to Quartz it's a java framework wich works with EE and SE editions and allows to define jobs to execute an specific time
Try this way ->
Firstly create a class TimeTask that runs your task, it looks like:
public class CustomTask extends TimerTask {
public CustomTask(){
//Constructor
}
public void run() {
try {
// Your task process
} catch (Exception ex) {
System.out.println("error running thread " + ex.getMessage());
}
}
}
Then in main class you instantiate the task and run it periodically started by a precised date:
public void runTask() {
Calendar calendar = Calendar.getInstance();
calendar.set(Calendar.DAY_OF_WEEK, Calendar.MONDAY);
calendar.set(Calendar.HOUR_OF_DAY, 15);
calendar.set(Calendar.MINUTE, 40);
calendar.set(Calendar.SECOND, 0);
calendar.set(Calendar.MILLISECOND, 0);
Timer time = new Timer(); // Instantiate Timer Object
// Start running the task on Monday at 15:40:00, period is set to 8 hours
// if you want to run the task immediately, set the 2nd parameter to 0
time.schedule(new CustomTask(), calendar.getTime(), TimeUnit.HOURS.toMillis(8));
}
Use Google Guava AbstractScheduledService as given below:
public class ScheduledExecutor extends AbstractScheduledService {
#Override
protected void runOneIteration() throws Exception {
System.out.println("Executing....");
}
#Override
protected Scheduler scheduler() {
return Scheduler.newFixedRateSchedule(0, 3, TimeUnit.SECONDS);
}
#Override
protected void startUp() {
System.out.println("StartUp Activity....");
}
#Override
protected void shutDown() {
System.out.println("Shutdown Activity...");
}
public static void main(String[] args) throws InterruptedException {
ScheduledExecutor se = new ScheduledExecutor();
se.startAsync();
Thread.sleep(15000);
se.stopAsync();
}
}
If you have more services like this, then registering all services in ServiceManager will be good as all services can be started and stopped together. Read here for more on ServiceManager.
If you want to stick with java.util.Timer, you can use it to schedule at large time intervals. You simply pass in the period you are shooting for. Check the documentation here.
Do something every one second
Timer timer = new Timer();
timer.schedule(new TimerTask() {
#Override
public void run() {
//code
}
}, 0, 1000);
These two classes can work together to schedule a periodic task:
Scheduled Task
import java.util.TimerTask;
import java.util.Date;
// Create a class extending TimerTask
public class ScheduledTask extends TimerTask {
Date now;
public void run() {
// Write code here that you want to execute periodically.
now = new Date(); // initialize date
System.out.println("Time is :" + now); // Display current time
}
}
Run Scheduled Task
import java.util.Timer;
public class SchedulerMain {
public static void main(String args[]) throws InterruptedException {
Timer time = new Timer(); // Instantiate Timer Object
ScheduledTask st = new ScheduledTask(); // Instantiate SheduledTask class
time.schedule(st, 0, 1000); // Create task repeating every 1 sec
//for demo only.
for (int i = 0; i <= 5; i++) {
System.out.println("Execution in Main Thread...." + i);
Thread.sleep(2000);
if (i == 5) {
System.out.println("Application Terminates");
System.exit(0);
}
}
}
}
Reference https://www.mkyong.com/java/how-to-run-a-task-periodically-in-java/
If your application is already using Spring framework, you have Scheduling built in
I use Spring Framework's feature. (spring-context jar or maven dependency).
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;
#Component
public class ScheduledTaskRunner {
#Autowired
#Qualifier("TempFilesCleanerExecution")
private ScheduledTask tempDataCleanerExecution;
#Scheduled(fixedDelay = TempFilesCleanerExecution.INTERVAL_TO_RUN_TMP_CLEAN_MS /* 1000 */)
public void performCleanTempData() {
tempDataCleanerExecution.execute();
}
}
ScheduledTask is my own interface with my custom method execute, which I call as my scheduled task.
You can also use JobRunr, an easy to use and open-source Java Scheduler.
To schedule a Job every 8 hours using JobRunr, you would use the following code:
BackgroundJob.scheduleRecurrently(Duration.ofHours(8), () -> yourService.methodToRunEvery8Hours());
If you are using Spring Boot, Micronaut or Quarkus, you can also use the #Recurring annotation:
public class YourService {
#Recurring(interval="PT8H")
public void methodToRunEvery8Hours() {
// your business logic
}
}
JobRunr also comes with an embedded dashboard that allows you to follow-up on how your jobs are doing.
Have you tried Spring Scheduler using annotations ?
#Scheduled(cron = "0 0 0/8 ? * * *")
public void scheduledMethodNoReturnValue(){
//body can be another method call which returns some value.
}
you can do this with xml as well.
<task:scheduled-tasks>
<task:scheduled ref = "reference" method = "methodName" cron = "<cron expression here> -or- ${<cron expression from property files>}"
<task:scheduled-tasks>
my servlet contains this as a code how to keep this in scheduler if a user presses accept
if(bt.equals("accept")) {
ScheduledExecutorService scheduler=Executors.newScheduledThreadPool(1);
String lat=request.getParameter("latlocation");
String lng=request.getParameter("lnglocation");
requestingclass.updatelocation(lat,lng);
}
There is a ScheduledFuture class in java.util.concurrent, it may helps you.

Timer and TimerTask in java

I would like to use Java Timer and TimerTask to do a Job everyday evening at 5 O' clock.
Please help me to solve this problem.
Problem with below methods as I think...
schedule(TimerTask task, Date time)
----Date can be specified for first day only not for forthcomingdays available.
schedule(TimerTask task, Date firstTime, long period)
----initial starting time and after how long it is to be executed can be given,
here if I start initlally my scheduler at 4 O' Clock evening then how to mention the next execution time. If I set 1 hour delay it will call after every one hour.
schedule(TimerTask task, long delay)
--This is not applicable which will do things based on start times.
schedule(TimerTask task, long delay, long period)
--This is not applicable which will do things based on start times.
I suggest you to switch to Quartz Cron Trigger which is very light and easy to use
SchedulerFactory sf = new StdSchedulerFactory();
Scheduler sched = sf.getScheduler();
//Job1 is scheduled to run everyday evening at 5 O' clock
JobDetail job = newJob(SimpleJob.class)
.withIdentity("job1", "group1")
.build();
CronTrigger trigger = newTrigger()
.withIdentity("trigger1", "group1")
.withSchedule(cronSchedule("0 0 17 * * ?"))
.build();
sched.scheduleJob(job, trigger);
well the more appropriate answer is the one by Grooveek
but as an alternative
import java.awt.Toolkit;
import java.util.Date;
import java.util.Timer;
import java.util.TimerTask;
public class demo
{
Toolkit toolkit;
Timer timer;
public demo()
{
toolkit = Toolkit.getDefaultToolkit();
timer = new Timer();
timer.schedule(new scheduleDailyTask(), 0, //initial delay
1 * 1000); //subsequent rate
}
class scheduleDailyTask extends TimerTask
{
public void run()
{
Date date = new Date();
if(date.getHours()==5 && date.getMinutes()==0 && date.getSeconds()==0)
{
System.out.println("its 5 O clock");
System.out.println("run the daily schedule method now");
}
}
}
public static void main(String args[]) {
new demo();
}
}
try
Calendar c = Calendar.getInstance();
c.clear(Calendar.MILLISECOND);
c.clear(Calendar.MINUTE);
c.clear(Calendar.SECOND);
if (c.get(Calendar.HOUR_OF_DAY) > 17) {
c.add(Calendar.DATE, 1);
}
c.set(Calendar.HOUR_OF_DAY, 17);
Date firstTime = c.getTime();
new Timer().scheduleAtFixedRate(task, firstTime, 24 * 3600 * 1000);

Run Java code once every hour

I'm tryng to write a simple Java program that runs some code every hour when the minute hand is at 20. The issue is that that the way I'm doing it is incredibly CPU intensive. I'm familiar with Quartz but I'm looking for a much simpler solution, any ideas?
boolean run = true;
while(run){
Calendar calendar = new GregorianCalendar();
int minute = calendar.get(Calendar.MINUTE);
if(minute == 20){
//Do some Stuff
}
}
A simple solution is to use the Executors framework:
final ScheduledExecutorService s = Executors.newSingleThreadScheduledExecutor();
s.scheduleAtFixedRate(task, secondsToFirstOccurence, 60*60, TimeUnit.SECONDS);
And use some logic to find out secondsToFirstOccurence. This will probably involve a Calendar instance, but would be much more convenient with JodaTime.
Be aware that if your application is running inside a managed environment (a web or ejb container) you're not allowed to use Thread.sleep() or any other thread-related operations, for that matter, take a look at the EJB restrictions page. I warn about this because the question is tagged java-ee, so the "simple application" might not be so simple after all - if it's running inside a Java EE container there are additional considerations to take care of.
If you're building an enterprise-grade application, forget about Thread.sleep(). Go for a full-fledged job scheduler, Use Quartz, it's an open source and extremely mature and reliable product. Or use Obsidian Scheduler, a feature-rich commercial scheduler with more out-of-the-box features than Quartz.
A lightweight alternative to a full-fledged scheduler (but suitable for running inside a container) would be to use the Timer service.
You might be looking for Thread.sleep() between calls
Look at java.util.Timer method scheduleAtFixedRate().
I would suggest that you remove the scheduling logic from your java program. By doing this you are able to focus only on what you want your program to do and leave the scheduling part to the OS. Also, say for example you decide at some point to write a c++ program that does what your java code does know, you won't have to implement the cron logic in your new programThat being said:
for Linux you have crontab
for Windows you have windows task schedule
for Mac, I am not sure, but given the fact it is UNIX based cron should be present.
Put your code in an infinite while and use
Thread.sleep(3600000);
Start the execution at 20 after
Example
while(1==1) {
//Your code here
try{
Thread.sleep(3600000);
}
catch (Exception e) {}
}
Schedule a cron job for the method that you want to execute hourly rather going for blocking sleep() call, Use some scheduling framework like quartz
You should have a look at ScheduledExecutorService
class BeeperControl {
private final ScheduledExecutorService scheduler =
Executors.newScheduledThreadPool(1);
public void beepForAnHour() {
final Runnable beeper = new Runnable() {
public void run() { System.out.println("beep"); }
};
final ScheduledFuture<?> beeperHandle =
scheduler.scheduleAtFixedRate(beeper, 10, 10, SECONDS);
scheduler.schedule(new Runnable() {
public void run() { beeperHandle.cancel(true); }
}, 60 * 60, SECONDS);
}
}
Use something like this
Calendar calendar = Calendar.getInstance();
calendar.set(Calendar.HOUR_OF_DAY, 20);
calendar.set(Calendar.MINUTE, 20);
calendar.set(Calendar.SECOND, 0);
Date time = calendar.getTime();
Timer timer = new Timer();
timer.schedule(new SomeTask(), time);
and then reschedule
So definitely the ScheduledExecutorService is fantastic as many of the other answers state.
In the event you're in a Java EE 6 server, you could have some fun with #Schedule and ScheduleExpression
See Have an EJB schedule tasks with "crontab syntax"
1) On first entry calculate next due time.
2) Use java.util.Timer.schedule()
3) Reschedule each run.
Code
package tests;
import java.util.Calendar;
import java.util.Date;
import java.util.Timer;
import java.util.TimerTask;
public class App201210130040 {
private static Timer timer = new Timer(false);
public static void schedule() {
Calendar due = Calendar.getInstance();
due.set(Calendar.MINUTE, 20);
if( due.before(Calendar.getInstance()) ) {
due.add(Calendar.HOUR, 1);
}
System.out.println("Scheduled to " + due.getTime().toString());
timer.schedule(new TimerTask() {
#Override
public void run() {
System.out.println("due");
schedule();
}
}, due.getTime());
}
public static void main(String[] args) {
schedule();
}
}
Another example
import java.text.SimpleDateFormat;
import java.util.Date;
public class TestHour {
private static final int MINUNTE = 20;
public static void main(String args[]) {
while (true) {
SimpleDateFormat bartDateFormat = new SimpleDateFormat("mm");
Date date = new Date();
int currentMin = new Integer(bartDateFormat.format(date))
.intValue();
if (currentMin < MINUNTE) {
sleepMinutes(MINUNTE - currentMin);
} else if (currentMin > MINUNTE) {
sleepMinutes(60 - currentMin + MINUNTE);
} else {
// DO SOMETHING EVERY HOUR
System.out.println("come on do it!!!");
sleepMinutes(60);
}
}
}
private static void sleepMinutes(int minutes) {
try {
System.out.println("Sleeping for " + minutes);
Thread.sleep(minutes * 1000*60);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
Yet even another example with the things learned today.
import java.util.Calendar;
import java.util.Date;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;
public class SchedulerExample2 implements Runnable{
public static void main(String args[]) {
Calendar due = Calendar.getInstance();
due.set(Calendar.MILLISECOND, 0);
due.set(Calendar.SECOND, 0);
due.set(Calendar.MINUTE, 20);
if (due.before(Calendar.getInstance())) {
due.add(Calendar.HOUR, 1);
}
long milliSecondsToNextOcurrence = due.getTimeInMillis() - new Date().getTime();
final ScheduledExecutorService s = Executors.newSingleThreadScheduledExecutor();
ShedulerExample task = new ShedulerExample();
s.scheduleAtFixedRate(task, milliSecondsToNextOcurrence, 60*60*1000, TimeUnit.MILLISECONDS);
}
#Override
public void run() {
System.out.println("hola->"+new Date());
}
}

How to use Timer class to call a method, do something, reset timer, repeat?

I'm a Java beginner and have been futzing around with various solutions to this problem and have gotten myself kind of knotted up. I've tried with Threads and then discovered this Timer class and have messed around with it without success so far. If you could post executable code with a main method so I could see it working and start playing around from there, that would be great.
Launch program
call doSomething()
Generate random number and set Timer for that long.
When Timer goes off, call doSomething() again.
Probably using this: http://docs.oracle.com/javase/6/docs/api/java/util/Timer.html
If you want to simply use Timer, I would do something like this:
public class TestClass {
public long myLong = 1234;
public static void main(String[] args) {
final TestClass test = new TestClass();
Timer timer = new Timer();
timer.schedule(new TimerTask() {
#Override
public void run() {
test.doStuff();
}
}, 0, test.myLong);
}
public void doStuff(){
//do stuff here
}
}
Sorry for the lousy identation.
Also, if you need to schedule execution of code, take a look at Guava Services since it can really make your code much clearer and abstract quite a bit of the boilerplate of creating threads, scheduling, etc.
By the way, I didn't take the trouble of generating random number, etc, but I think you can figure out how to include that part. I hope this is enough to get you on the right track.
For the record, if you were to use Guava, it would look something like this:
class CrawlingService extends AbstractScheduledService {
#Override
protected void runOneIteration() throws Exception {
//run this alot
}
#Override
protected void startUp() throws Exception {
//anything you need to step up
}
#Override
protected void shutDown() throws Exception {
//anything you need to tear down
}
#Override
protected Scheduler scheduler() {
return new CustomScheduler() {
#Override
protected Schedule getNextSchedule() throws Exception {
long a = 1000; //number you can randomize to your heart's content
return new Schedule(a, TimeUnit.MILLISECONDS);
}
};
}
}
And you would simply create a main that called new CrawlingService.start(); that's it.
Do you specifically want a Timer? If not you're probably better off with a ScheduledExecutorService and calling scheduleAtFixedRate or scheduleWithFixedDelay; quoting the Javadocs:
Java 5.0 introduced the java.util.concurrent package and one of the
concurrency utilities therein is the ScheduledThreadPoolExecutor which
is a thread pool for repeatedly executing tasks at a given rate or
delay. It is effectively a more versatile replacement for the
Timer/TimerTask combination, as it allows multiple service threads,
accepts various time units, and doesn't require subclassing TimerTask
(just implement Runnable). Configuring ScheduledThreadPoolExecutor
with one thread makes it equivalent to Timer.
UPDATE
Here's some working code using a ScheduledExecutorService:
import java.util.Date;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;
public class Test {
public static void main(String[] args) {
final ScheduledExecutorService ses = Executors.newSingleThreadScheduledExecutor();
ses.scheduleWithFixedDelay(new Runnable() {
#Override
public void run() {
System.out.println(new Date());
}
}, 0, 1, TimeUnit.SECONDS);
}
}
The output looks like:
Thu Feb 23 21:20:02 HKT 2012
Thu Feb 23 21:20:03 HKT 2012
Thu Feb 23 21:20:04 HKT 2012
Thu Feb 23 21:20:05 HKT 2012
Thu Feb 23 21:20:06 HKT 2012
Thu Feb 23 21:20:07 HKT 2012
Think of a scenario where I want my code to execute at a particular time in my application or at sometime later from the current time. In other words, I want to schedule my task at the definite time.
Java Timer class (java.util.Timer) allows an application to schedule the task on a separate background thread.
Here is the simplest example of Java Timer:
import java.util.Timer;
import java.util.TimerTask;
public class JavaTimer {
public static void main(String[] args) {
Timer timer = new Timer();
TimerTask task = new TimerTask() {
#Override
public void run() {
System.out.println("Inside Timer Task" + System.currentTimeMillis());
}
};
System.out.println("Current time" + System.currentTimeMillis());
timer.schedule(task, 10000,1000);
System.out.println("Current time" + System.currentTimeMillis());
}
}
Output:
Current time1455469505220
Current time1455469505221
Inside Timer Task1455469515222
Inside Timer Task1455469516222
Inside Timer Task1455469517222
Inside Timer Task1455469518222
Inside Timer Task1455469519222
Inside Timer Task1455469520222
Inside Timer Task1455469521222
Inside Timer Task1455469522222
Inside Timer Task1455469523222
Inside Timer Task1455469524222
Inside Timer Task1455469525222
Inside Timer Task1455469526222
Inside Timer Task1455469527222
Inside Timer Task1455469528223
Inside Timer Task1455469529223 and it goes on
ANALYSIS :
The call to timer.schedule(task, 10000,1000) is going to schedule the task which is going to execute for first time (on another thread) after 10 second from this call. After that it will call again after delay of 10 seconds. It is important to mention here that if the task cannot be started after 10 seconds, next task call will not get pre-pond. So here the delay time between two consecutive task is fixed.
Source: Java Timer Example
If you don't want to use timer class and can use Quartz then perform it like. My main class would be
import com.google.common.util.concurrent.AbstractScheduledService;
import org.quartz.CronScheduleBuilder;
import org.quartz.JobBuilder;
import org.quartz.JobDetail;
import org.quartz.impl.StdSchedulerFactory;
import org.quartz.*;
import org.quartz.impl.StdSchedulerFactory;
import static org.quartz.TriggerBuilder.newTrigger;
import java.util.concurrent.CountDownLatch;
public class Test {
public static void main(String[] args) throws Exception{
CountDownLatch latch = new CountDownLatch(1);
//do schdeuling thing
JobDetail job = JobBuilder.newJob(SimpleJob.class).withIdentity(
"CronQuartzJob", "Group").build();
// Create a Trigger that fires every 5 minutes.
Trigger trigger = newTrigger()
.withIdentity("TriggerName", "Group")
.withSchedule(CronScheduleBuilder.cronSchedule("0/1 * * * * ?"))
.build();
// Setup the Job and Trigger with Scheduler & schedule jobs
final Scheduler scheduler = new StdSchedulerFactory().getScheduler();
scheduler.start();
scheduler.scheduleJob(job, trigger);
//
latch.await();
Runtime.getRuntime().addShutdownHook(new Thread(new Runnable() {
#Override
public void run() {
try {
scheduler.shutdown();
latch.countDown();
}catch (Exception e){
e.printStackTrace();
}
}
}));
}
}
and job class would be
import org.quartz.Job;
import org.quartz.JobExecutionContext;
import org.quartz.JobExecutionException;
public class SimpleJob implements Job {
public void execute(JobExecutionContext jobExecutionContext) throws JobExecutionException {
System.out.println("executing task!");
}
}
I would create a executable jar for this and start this using java -jar .. & and Ctrl+C can stop that process , If you want it in background disownit
The below code will run at 18:20 and it will repeat itself in interval of 5 sec.
public static void main(String[] args) {
Timer timer = new Timer();
TimerTask tt = new TimerTask() {
public void run() {
Calendar cal = Calendar.getInstance();
int hour = cal.get(Calendar.HOUR_OF_DAY);
int min = cal.get(Calendar.MINUTE);
if (hour == 18 && min == 20) {
doSomething();
}
}
};
timer.schedule(tt, 1000, 5000);
}

How to set the time?

suppose i want to start the execution of the thread at some specific time,at time which i want,how can i set the time in below code so that i can start the thread at specific time and after that same thread will keep executing after given interval of time.
(in sample code ,suppose i want to start the beeper at midnight,how can i do that?
class BeeperControl {
private final ScheduledExecutorService scheduler =
Executors.newScheduledThreadPool(1);
public void beepForAnHour() {
final Runnable beeper = new Runnable() {
public void run() { System.out.println("beep"); }
};
final ScheduledFuture<?> beeperHandle =
scheduler.scheduleAtFixedRate(beeper, 10, 10, SECONDS);
scheduler.schedule(new Runnable() {
public void run() { beeperHandle.cancel(true); }
}, 60 * 60, SECONDS);
}
}
Thanks in advance.
Look into Timer and TimerTask classes.
For advanced scheduling needs, look into Quartz job scheduler.
If you want to run the beeper after midnight, you need to change the initialDelay that you pass into the scheduler. Work out how much delay you need by subtracting the current time from midnight. This is shown below:
private static Date getMidnight(){
Calendar cal = new GregorianCalendar();
cal.add(Calendar.DAY_OF_MONTH,1);
cal.set(Calendar.HOUR_OF_DAY, 0);
cal.set(Calendar.MINUTE, 0);
cal.set(Calendar.SECOND, 0);
return cal.getTime();
}
long initialDelay = (getMidnight().getTime() - System.currentTimeMillis())/1000;
final ScheduledFuture<?> beeperHandle = scheduler.scheduleAtFixedRate(beeper, initialDelay, 10, SECONDS);
Initially schedule it by checking the difference between the current time and when you want to run the task. Then use the scheduleAtFixedRate..
However be warned, the thread need not be scheduled at the exact time you need it..

Categories

Resources