Results 1 to 20 of 20
  1. #1
    AmFreak is offline Member
    Join Date
    Jul 2011
    Posts
    34
    Rep Power
    0

    Default How to stop ScheduledExecutorService?

    Hi,

    i have a list of instances. Each instance starts a ScheduledExecutorService like this

    Java Code:
    scheduler = Executors.newScheduledThreadPool( 1 );
    		scheduler.scheduleAtFixedRate(new Runnable() {
    			@Override public void run() {
    
                          // do work ....
                         // ....
                         // .... 
         }      
    		 },
    		      delay,
    		      interval,
    		      TimeUnit.MILLISECONDS );
    The problem i now have is that a thread uses data (only reading) that can be deleted elsewhere. So before i delete that data, i have to stop the thread that uses that data. I now don't know how to handle that problem right. The only idea i currently have is sending an interrupt from the main thread and checking if the thread is interrupted in the "do work" part. Then running a loop in the main thread to check if the scheduler was stopped. And after it was stopped deleting the data. But this is kind of ugly cause of the 100% cpu time of the checking loop. I also don't know if this is safe cause of the documentation of the method shutdownNow

    Attempts to stop all actively executing tasks, halts the processing of waiting tasks, and returns a list of the tasks that were awaiting execution.
    There are no guarantees beyond best-effort attempts to stop processing actively executing tasks. For example, typical implementations will cancel via Thread.interrupt(), so any task that fails to respond to interrupts may never terminate.

  2. #2
    Norm's Avatar
    Norm is offline Moderator
    Join Date
    Jun 2008
    Location
    SW Missouri
    Posts
    17,271
    Rep Power
    25

    Default Re: How to stop ScheduledExecutorService?

    Could you make a small program that compiles and executes (SSCCE) and shows your problem.
    I'm sure there is a better way to know when an event has happened than to use a while loop.

  3. #3
    AmFreak is offline Member
    Join Date
    Jul 2011
    Posts
    34
    Rep Power
    0

    Default Re: How to stop ScheduledExecutorService?

    Thanks for the answer!
    That's bascially what i have:

    Java Code:
    public class SchedulerTest {
    
    	/**
    	 * @param args
    	 */
    	public static void main(String[] args) {
    		int a = 25;
    		MyScheduler ms = new MyScheduler();
    		ms.start(a);
    	}	
    }
    Java Code:
    import java.util.concurrent.Executors;
    import java.util.concurrent.ScheduledExecutorService;
    import java.util.concurrent.TimeUnit;
    
    
    public class MyScheduler {
    	
    	private ScheduledExecutorService scheduler;
    
    	public void start(final int a)                // start(final Stock stock) in my program
    	{
    		scheduler = Executors.newScheduledThreadPool( 1 );
    		scheduler.scheduleAtFixedRate(new Runnable() {
    			@Override public void run() {
    				System.out.println(a); 	
    		     }      
    		 },
    		      0,
    		      1000,
    		      TimeUnit.MILLISECONDS );
    	}
    }
    But in my program a isn't an int. a is an object. My program is a gui with a list of stocks. When the user adds a new stock it's saved in a database in a table named stock (all done with JPA). My program then starts a new Scheduler by making a new MyScheduler instance and calling the start(final Stock stock) method. The actual rate of the stock is now retrieved every hour (from an internet server) and written to the db in the table stockPrice. The stock is needed for the foreign key of the table stockPrice. The user can also delete a stock (and with it all it stock rates are deleted) and thats where my problem happens. Cause of the stock used in the thread, i have to stop the thread before the stock is deleted cause otherwise the thread would use a stock that no longer exists. So basically if the user wants to delete a stock i have first to make sure that the thread with that stock is stopped before deleting that stock and that's where my original question is coming from. Hope i have it explained better now :)

  4. #4
    Norm's Avatar
    Norm is offline Moderator
    Join Date
    Jun 2008
    Location
    SW Missouri
    Posts
    17,271
    Rep Power
    25

    Default Re: How to stop ScheduledExecutorService?

    What am I supposed to see when I execute the code?
    running a loop in the main thread to check
    Where is the while loop you were talking about?

    How does this code demonstrate the problem mentioned here:
    i have to stop the thread that uses that data. I now don't know how to handle that problem right.

  5. #5
    AmFreak is offline Member
    Join Date
    Jul 2011
    Posts
    34
    Rep Power
    0

    Default Re: How to stop ScheduledExecutorService?

    Ok i have put together a little example program to ilustrate my problem.
    Download here (the little green/white download button) - tried to upload it here, but it failed 3 times.
    You have to uncomment the
    Java Code:
    <!-- <property name="eclipselink.ddl-generation" value="drop-and-create-tables" /> -->
    line in the persistence.xml the first time you run it and it creates a database on your main partiton if you are on Windows:
    Java Code:
    <property name="javax.persistence.jdbc.url"
    				value="jdbc:derby:/database/test;" />
    Heres the code without the model:


    Java Code:
    public SchedulerTest(){
    		
    		factory = Persistence.createEntityManagerFactory(PERSISTENCE_UNIT_NAME);
    		EntityManager em = factory.createEntityManager();
    
    		// Begin a new local transaction so that we can persist a new entity
    		em.getTransaction().begin();
    
    		// Read the existing entries
    		Query q = em.createQuery("select m from Person m");
    		// Persons should be empty
    
    		// Do we have entries?
    		boolean createNewEntries = (q.getResultList().size() == 0);
    
    		Family family = new Family();
    		family.setDescription("Family for the Knopfs");
    		em.persist(family);
    		
    		
    		// No, so lets create new entries
    		if (createNewEntries) {
    			
    		
    			family = new Family();
    			family.setDescription("Family for the Hoffs");
    			em.persist(family);
    			family = new Family();
    			family.setDescription("Family for the Dots");
    			em.persist(family);
    			for (int i = 0; i < 40; i++) {
    				Person person = new Person();
    				person.setFirstName("Jim_" + i);
    				person.setFamily(family);
    				family.getMembers().add(person);
    				em.persist(person);
    				// Now persists the family person relationship
    				family.getMembers().add(person);
    				em.persist(person);
    				em.persist(family);
    			}
    		}
    
    		em.getTransaction().commit();
    		
    		TypedQuery<Family> q2 = em.createQuery("select f from Family f", Family.class);
    
    		if (q2.getResultList().size() > 0)
    			families = (List<Family>) q2.getResultList();
    			
    		 MyScheduler ms = new MyScheduler(factory);
    	     ms.start(families.get(0));
    		
    	     try {
    			Thread.sleep(5000);
    		} catch (InterruptedException e) {
    			e.printStackTrace();
    		}
    	     
    	     System.out.println("Awake");
    	     
    	     em.remove(families.get(0));                          // <---- Problem here - family 0 is removed from database while the other thread uses it as a foreign key for the database
    	     em.getTransaction().begin();
    	     em.getTransaction().commit();
    	     
    	     em.close();
    	     
    	    }
    Java Code:
    public class MyScheduler {
    	
    	private ScheduledExecutorService scheduler;
    	private EntityManager em;
    
    	public MyScheduler(EntityManagerFactory factory) {
    		em = factory.createEntityManager();
    	}
    
    	public void start(final Family family)
    	{
    		scheduler = Executors.newScheduledThreadPool( 1 );
    		scheduler.scheduleAtFixedRate(new Runnable() {
    			@Override public void run() {
    				System.out.println(family.getDescription());
    				Person person = new Person();
    				person.setFirstName("ABC");
    				person.setFamily(family);
    				family.getMembers().add(person);
    				em.persist(person);
    				em.getTransaction().begin();
    				em.getTransaction().commit();
    		     }      
    		 },
    		      0,
    		      1000,
    		      TimeUnit.MILLISECONDS );
    	}
    }
    As you can see by running it, it creates an error cause the family is removed from database while the other thread uses it as a foreign key for the database.

  6. #6
    Norm's Avatar
    Norm is offline Moderator
    Join Date
    Jun 2008
    Location
    SW Missouri
    Posts
    17,271
    Rep Power
    25

    Default Re: How to stop ScheduledExecutorService?

    I asked for a small, simple program for testing. The download is 8M???
    I'm not interested in installing all that on my computer.

    I looked through the API doc for the ScheduledExecutorService class and others and saw this:
    // Otherwise, the task will only terminate via cancellation or termination of the executor.
    That would mean there are methods to call to do what you want.
    Have you looked through the API docs to see where you can terminate or cancel the task?

  7. #7
    AmFreak is offline Member
    Join Date
    Jul 2011
    Posts
    34
    Rep Power
    0

    Default Re: How to stop ScheduledExecutorService?

    The dl is 8 MB cause i included the needed libs (derby / eclipselink / persistencex) to run it. My program is 4 classes the 2 shown above + the 2 model classes (person / family). As said in my first post i can call shutdownNow, but as the docu says:
    There are no guarantees beyond best-effort attempts to stop processing actively executing tasks. For example, typical implementations will cancel via Thread.interrupt(), so any task that fails to respond to interrupts may never terminate.
    there's no guarantee that the task may terminate. The other problem is what to do in my main thread, cause i can only go on in my main thread if the scheduler has stopped. That's for what the loop would have been for like:

    Java Code:
    while (!scheduler.isShutDown) { }
    delete stock
    but this doesn't seem to be the right way (cause of the 100% cpu utilization of the while loop and i don't know if it's safe) so i asked if there is a better way. As i am fairly new to this is just hoped someone in the knows would show me the way or give me a hint :)

  8. #8
    Norm's Avatar
    Norm is offline Moderator
    Join Date
    Jun 2008
    Location
    SW Missouri
    Posts
    17,271
    Rep Power
    25

    Default Re: How to stop ScheduledExecutorService?

    Have you looked at the API doc to see what the possibilities are for terminating or cancellation of the task?

  9. #9
    AmFreak is offline Member
    Join Date
    Jul 2011
    Posts
    34
    Rep Power
    0

    Default Re: How to stop ScheduledExecutorService?

    shutDown and shutDownNow are the methods the scheduler has for stopping. shutDownNow sends an interrupt that's why i mentioned to check for interrupts between the "work code" in the scheduler. Seems there is no working general option though:

    Java Code:
    What if a thread doesn't respond to Thread.interrupt?
    In some cases, you can use application specific tricks. For example, if a thread is waiting on a known socket, you can close the socket to cause the thread to return immediately. Unfortunately, there really isn't any technique that works in general. It should be noted that in all situations where a waiting thread doesn't respond to Thread.interrupt, it wouldn't respond to Thread.stop either. Such cases include deliberate denial-of-service attacks, and I/O operations for which thread.stop and thread.interrupt do not work properly.
    have to test it then it seems.
    The problem with the loop remains though :/

  10. #10
    Norm's Avatar
    Norm is offline Moderator
    Join Date
    Jun 2008
    Location
    SW Missouri
    Posts
    17,271
    Rep Power
    25

    Default Re: How to stop ScheduledExecutorService?

    methods the scheduler has for stopping.
    What about the task? The message I saw talked about the task not the scheduler.

    If the task is in a loop, you will need to tell it to stop looping.

  11. #11
    AmFreak is offline Member
    Join Date
    Jul 2011
    Posts
    34
    Rep Power
    0

    Default Re: How to stop ScheduledExecutorService?

    The task is the "do work" code in the scheduler that is repeated periodically by the scheduler. It is repeated forever till it encounters an exception or the scheduler is shutDown. The task itself is not in a loop the scheduler is like a loop though, cause it repeats the task every nth timeperiod (set by the interval) forever till shutDown.
    Last edited by AmFreak; 01-31-2012 at 04:15 AM.

  12. #12
    Norm's Avatar
    Norm is offline Moderator
    Join Date
    Jun 2008
    Location
    SW Missouri
    Posts
    17,271
    Rep Power
    25

    Default Re: How to stop ScheduledExecutorService?

    Have you looked at the object returned by scheduleAtFixedRate()?
    Does it have a method you could use to stop the task from executing?

  13. #13
    AmFreak is offline Member
    Join Date
    Jul 2011
    Posts
    34
    Rep Power
    0

    Default Re: How to stop ScheduledExecutorService?

    It has a cancel method but that does basically send an interrupt:
    Attempts to cancel execution of this task. This attempt will fail if the task has already completed, has already been cancelled, or could not be cancelled for some other reason. If successful, and this task has not started when cancel is called, this task should never run. If the task has already started, then the mayInterruptIfRunning parameter determines whether the thread executing this task should be interrupted in an attempt to stop the task.
    It all seem to boil down to sending an interrupt so this seems to be the right way. The bigger problem i have is how to wait for the stopping in the main thread.

  14. #14
    Norm's Avatar
    Norm is offline Moderator
    Join Date
    Jun 2008
    Location
    SW Missouri
    Posts
    17,271
    Rep Power
    25

    Default Re: How to stop ScheduledExecutorService?

    Have you tried testing using the cancel method to see what the task sees when cancel is called?
    If the task can detect it is being cancelled it could pass that info to the main thread just before it exited.
    Perhaps by starting a task to do what the main thread wanted to do when the task ended.

    Have you looked at the Lock and Semaphore classes as a way for one thread to way for the other to finish.
    Last edited by Norm; 01-31-2012 at 07:44 PM.

  15. #15
    AmFreak is offline Member
    Join Date
    Jul 2011
    Posts
    34
    Rep Power
    0

    Default Re: How to stop ScheduledExecutorService?

    If i call scheduler.shutDownNow (and thus send an interrupt) from the main Thread and test between the code in the scheduler like this:

    Java Code:
    scheduler.scheduleAtFixedRate(new Runnable() {
    			@Override public void run() {
    				       // do work
    					if(Thread.interrupted())
    						return;
                       // do work
                       // ....
                       if(Thread.interrupted())
    						return;
    		     }
    the scheduler stops as soon as it aproaches a if(Thread.interrupted)) line.
    But my problem lies in the code in the mainThread cause i have to make sure that the mainThread only goes along after the Scheduler is stopped. That's what i meant with the 100% cpu loop, cause i don't know how to implement this aside from a 100% cpu loop like this:
    Java Code:
      while(!myScheduler.getScheduler().isShutdown()) { }
    
               // next main Thread code
    I think i should do the scheduler stopping and the stock deleting in the mainThread cause otherwise the user could click the delete button to delete one or more marked stocks and make other things in the gui (like try to delete again, or changing a soon to be deleted stock etc..) between the clicking and the real deleting of the stocks. There seems to be a method for this for "Thread" called join() that waits for the Thread to die before going ahead with the following code, but nothing like it for scheduler.

  16. #16
    Norm's Avatar
    Norm is offline Moderator
    Join Date
    Jun 2008
    Location
    SW Missouri
    Posts
    17,271
    Rep Power
    25

    Default Re: How to stop ScheduledExecutorService?

    Have you looked at the Lock or Semaphore classes as a way for one thread to way for the other to finish.
    The main thread calls method to stop the task and then waits for the task to end by using one of the above classes. The task as it exits, calls a method of those classes that will release the main thread from its wait.

  17. #17
    AmFreak is offline Member
    Join Date
    Jul 2011
    Posts
    34
    Rep Power
    0

    Default Re: How to stop ScheduledExecutorService?

    Have looked at these classes, but they seem to be for managing the access to objects from different threads. I mean i could lock the stock everytime the thread is working, so the main thread has to wait for the lock to be released. I have it currently done this way though:

    Java Code:
    public class MyScheduler {
    
    private Thread thread;
    ....
    ....
    	public void start(final Family family)
    	{
    
    scheduler.scheduleAtFixedRate(new Runnable() {
                @Override public void run() {
                         thread = Thread.currentThread();
                           // do work
                        if(Thread.interrupted())
                            return;
                       // do work
                       // ....
                       if(Thread.interrupted())
                            return;
    ...
                 }
    In main Thread:
    Java Code:
    	     ms.getScheduler().shutdownNow();
    	    try {
    			ms.getThread().join();
    		} catch (InterruptedException e) {
    			// TODO Auto-generated catch block
    			e.printStackTrace();
    		}

  18. #18
    Norm's Avatar
    Norm is offline Moderator
    Join Date
    Jun 2008
    Location
    SW Missouri
    Posts
    17,271
    Rep Power
    25

    Default Re: How to stop ScheduledExecutorService?

    managing the access to objects from different threads.
    I thought that was your problem: two threads, one resource

    Does your code work?

  19. #19
    AmFreak is offline Member
    Join Date
    Jul 2011
    Posts
    34
    Rep Power
    0

    Default Re: How to stop ScheduledExecutorService?

    Quote Originally Posted by Norm View Post
    I thought that was your problem: two threads, one resource
    Wouldn't a lock mean i can't change the stock at the same time it's used in the thread e.g. changing it's description or name in the main Thread? The code works i strangely get a database error though if the scheduler is canceled before the database part of the scheduler is executed.

  20. #20
    Norm's Avatar
    Norm is offline Moderator
    Join Date
    Jun 2008
    Location
    SW Missouri
    Posts
    17,271
    Rep Power
    25

    Default Re: How to stop ScheduledExecutorService?

    I'd use the lock/semaphore at the point you wanted the main thread to wait for the task to end just before cancelling the task.
    The task would free the lock/semaphore as it exited releasing the main thread.

Similar Threads

  1. New to java stop need help stop
    By Skrap09 in forum New To Java
    Replies: 3
    Last Post: 09-17-2011, 12:45 PM
  2. Replies: 0
    Last Post: 02-21-2011, 09:36 AM
  3. Use stop button to stop moving (stop timers) on JPanel
    By mneskovic in forum New To Java
    Replies: 3
    Last Post: 07-23-2010, 12:50 PM
  4. How to stop SwingWorker?
    By JStarter in forum AWT / Swing
    Replies: 14
    Last Post: 07-20-2010, 04:36 PM
  5. Can you stop a gif? xd
    By Exhonour in forum New To Java
    Replies: 0
    Last Post: 01-16-2009, 08:44 PM

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •