The idea is for my runnable to run every minute.
Instead, it runs in roughly about 20 seconds and I have no idea why.
Below is the code:
final Handler handler = new Handler();
Runnable runnable = new Runnable() {
#Override
public void run() {
try{
//Post from Queue & update post
if (NetworkUtils.isConnected()) {
//post from queue
try {
postHelper.postFromQueue();
} catch (IOException e) {
e.printStackTrace();
}
//Update posts
postHelper.updateSolicitations();
}
}
catch (Exception e) {
// TODO: handle exception
}
finally{
//also call the same runnable to call it at regular interval
handler.postDelayed(this, 60000);
}
}
};
I don't know if it's relevant but it's onCreate method of MainActivity.
Maybe you consider using ScheduledExecutorService
public static void main(String[] args) {
ScheduledExecutorService execService
= Executors.newScheduledThreadPool(5);
execService.scheduleAtFixedRate(()->{
//The repetitive task, say to update Database
System.out.println("hi there at: "+ new java.util.Date());
}, Delay, Rate, TimeUnit.MILLISECONDS );//TimeUnit.MILLISECONDS is time unit
}
Use a scheduled where you define a quartz cronjob that is then triggered whenever you defined it.
you can do something like every minute or second or every day at 3 o'clock
Simple Quartz/Cron job setup
Handler handler = new Handler();
handler.postDelayed(new Runnable() {
#Override
public void run() {
try{
//Post from Queue & update post
if (NetworkUtils.isConnected()) {
//post from queue
try {
postHelper.postFromQueue();
} catch (IOException e) {
e.printStackTrace();
}
//Update posts
postHelper.updateSolicitations();
}
}
catch (Exception e) {
// TODO: handle exception
}
}
}, 60000);
Related
I'm using this code to Schedule a Task in my Java 8 Spring WebApp:
In a #Controller;
#EventListener(ContextRefreshedEvent.class)
public void doSomethingAfterContextRefreshed() {
ScheduledFuture<?> countdown = scheduler.schedule(new Runnable() {
#Override
public void run() {
try {
Execute();
} catch (IOException e) {
e.printStackTrace();
}
}}, 10, TimeUnit.SECONDS);
while (!countdown.isDone()) {
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
scheduler.shutdown();
}
When the App starts, the Execute() method gets called 10 seconds after startup with no errors, but after it completes I get the following stack trace:
java.util.concurrent.RejectedExecutionException: Task java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask#52518e6[Not completed, task = java.util.concurrent.Executors$RunnableAdapter#759546c8[Wrapped task = com.mycompany.myproject.service.LoadService$1#4871ba3f]] rejected from java.util.concurrent.ScheduledThreadPoolExecutor#798daafa[Terminated, pool size = 0, active threads = 0, queued tasks = 0, completed tasks = 1]
at java.base/java.util.concurrent.ThreadPoolExecutor$AbortPolicy.rejectedExecution(ThreadPoolExecutor.java:2055)
at java.base/java.util.concurrent.ThreadPoolExecutor.reject(ThreadPoolExecutor.java:825)
at java.base/java.util.concurrent.ScheduledThreadPoolExecutor.delayedExecute(ScheduledThreadPoolExecutor.java:340)
at java.base/java.util.concurrent.ScheduledThreadPoolExecutor.schedule(ScheduledThreadPoolExecutor.java:562)
Any ideas why I get this exception?
Let's simplify this:
public class DeleteMe {
public static void main(String[] args) {
doSomethingAfterContextRefreshed();
doSomethingAfterContextRefreshed();
}
static ScheduledThreadPoolExecutor scheduler = new ScheduledThreadPoolExecutor(1);
public static void doSomethingAfterContextRefreshed() {
ScheduledFuture<?> countdown = scheduler.schedule(new Runnable() {
#Override
public void run() {
System.out.println("Some message");
}}, 100, TimeUnit.MILLISECONDS);
while (!countdown.isDone()) {
LockSupport.parkNanos(TimeUnit.MILLISECONDS.toNanos(10));
}
scheduler.shutdown();
}
}
At the end of the first invocation of doSomethingAfterContextRefreshed - what do you do? scheduler.shutdown();.
At the second invocation of doSomethingAfterContextRefreshed(); what do you do? scheduler.schedule(....).
Is the scheduler shutdown at this point in time? What does the documentation of schedule says to throw in such cases? You have your answer now.
I'm trying to implement a method that continuously run a SQL query until it returns results or fails after x seconds.
Currently my method uses CountDownLatch:
final CountDownLatch done = new CountDownLatch(1);
new Thread(new Runnable()
{
#Override
public void run() {
try
{
getQueryResults(sql);
}
catch (Exception e)
{
// TODO Auto-generated catch block
e.printStackTrace();
}
done.countDown();
}
}).start();
return done.await(30, TimeUnit.SECONDS);
Are there better ways of doing this?
i am trying to write a method that pings my database every hour. In doing so I am having some difficulties in sleeping the Thread is it might not have been initialised
private void pingServer(){
final Thread serverPing = new Thread(new Runnable() {
#Override
public void run() {
Connection conn = null;
try {
conn = source.getConnection();
while(conn.isValid(3600)){
//no need to do anything as conn.isValid does the ping
serverPing.sleep(3600000);
}
} catch (SQLException | InterruptedException e) {}
finally{
closeConnection(conn);
}
}
});
serverPing.setDaemon(true);
serverPing.start();
}
How can i modify this code to initialise it correctly?
Thanks
To sleep, just use Thread.sleep(3600000);
Yet, you should use a ScheduledExecutorService for this kind of tasks:
ScheduledExecutorService ses = Executors.newSingleThreadScheduledExecutor();
ses.scheduleAtFixedRate(new Runnable() {
#Override
public void run() {
try(Connection conn = source.getConnection()){
if(!conn.isValid(3600)){
// do something if the connection is invalid
}
}
}
}, 0, 1, TimeUnit.HOURS);
Just use Thread.sleep(TIME_GAP); to sleep the current thread.
Example
while(conn.isValid(3600)){
try {
Thread.sleep(3600000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
...
Thread showWordThread = new Thread() {
public void run() {
try {
sleep(config.delayTime * 1000);
} catch (Exception e) {
System.out.println(e.toString());
}
this.run();
}
};
showWordThread.run();
}
...
It had run for about 5 minutes before error occured:
Exception in thread "Thread-2" java.lang.StackOverflowError.
Why?
I had tried this:
Thread showWordThread = new Thread(new Runnable() {
public void run() {
while (true) {
try {
Thread.sleep(config.delayTime * 1000);
} catch (Exception e) {
System.out.println(e.toString());
}
}
}
});
showWordThread.start();
But error still occured.
Others have explained that you should use a while loop instead. You're also trying to call the run method inside your anonymous class declaration. Additionally, you should call start, rather than run - when the new thread has started, it will call run automatically. I'd actually suggest implementing Runnable rather than extending Thread, too. So you want:
Thread showWordThread = new Thread(new Runnable() {
#Override public void run() {
while (someCondition) {
try {
Thread.sleep(config.delayTime * 1000);
// Presumably do something useful here...
} catch (Exception e) {
System.out.println(e.toString());
}
}
}
});
showWordThread.start();
Alternatively, consider using a Timer or ScheduledExecutorService.
You are calling run method as recursively. Java holds call information(such as parameters) in stack memory so when you are calling a method recursively and there isn't any end point, stack memory will consumed and StackOverflow exception throws.
Maybe you want increasing Heap Size of JVM but this solution don't solve your problem and StackOverflow will occurred .
I guess you want run a thread continually. I recommend following code:
Thread showWordThread = new Thread()
{
public void run()
{
try
{
sleep(config.delayTime * 1000);
}
catch (Exception e)
{
System.out.println(e.toString());
}
// this.run(); this snnipet code make error
}
};
showWordThread.run();
}
Don't call run() from within the run() method. That'll definitely produce a stack overflow because you keep reentering the same method with no exit condition. Instead use a while loop.
Thread showWordThread = new Thread() {
public void run() {
while(condition) {
try {
sleep(config.delayTime * 1000);
} catch (Exception e) {
System.out.println(e.toString());
}
}
};
showWordThread.start();
}
Your code have infinity recursive, you should change the code to:
Thread showWordThread = new Thread() {
public void run() {
while (true) {
try {
Thread.sleep(config.delayTime * 1000);
} catch (Exception e) {
System.out.println(e.toString());
}
}
}
};
showWordThread.start();
Your function calls itself each time you run it.
That results in a stack overflow.
Maybe because you call run method (this.run()) from itself?
Sorry if the question is quite simple. I am a beginner.
I have to create thread that calulates something, while the first thread works the other one have to measure if the first thread calculate the function in specified time. If not, it has to throw exception. Else it returns the answer.
I'd take the java.util.concurrent components - simple example
public void myMethod() {
// select some executor strategy
ExecutorService executor = Executors.newFixedThreadPool(1);
Future f = executor.submit(new Runnable() {
#Override
public void run() {
heresTheMethodToBeExecuted();
}
});
try {
f.get(1000, TimeUnit.MILLISECONDS);
} catch (InterruptedException e) {
// do something clever
} catch (ExecutionException e) {
// do something clever
} catch (TimeoutException e) {
// do something clever
}
}
Have your thread notify a synchronization object when it is done and have your other thread wait x number of milliseconds for it to finish.
public class Main {
private static final Object mThreadLock = new Object();
static class DoTaskThread extends Thread {
public void run() {
try {
int wait = new Random().nextInt(10000);
System.out.println("Waiting " + wait + " ms");
Thread.sleep(wait);
} catch (InterruptedException ex) {
}
synchronized (mThreadLock) {
mThreadLock.notifyAll();
}
}
}
/**
* #param args the command line arguments
*/
public static void main(String[] args) {
synchronized (mThreadLock) {
DoTaskThread thread = new DoTaskThread();
thread.start();
try {
// Only wait 2 seconds for the thread to finish
mThreadLock.wait(2000);
} catch (InterruptedException ex) {
}
if (thread.isAlive()) {
throw new RuntimeException("thread took too long");
} else {
System.out.println("Thread finished in time");
}
}
}
}
join is a lot simpler than using a lock.
join (millis)
Waits at most millis milliseconds
for this thread to die. A timeout of 0
means to wait forever.
Example code:
Thread calcThread = new Thread(new Runnable(){
#Override
public void run() {
//some calculation
}
});
calcThread.start();
//wait at most 2secs for the calcThread to finish.
calcThread.join(2000);
//throw an exception if the calcThread hasn't completed.
if(calcThread.isAlive()){
throw new SomeException("calcThread is still running!");
}
Have a look at http://download.oracle.com/javase/1.5.0/docs/api/java/util/concurrent/ExecutorService.html#awaitTermination(long,%20java.util.concurrent.TimeUnit) which allows you to handle this without dealing with thread synchronization yourself.