2013-01-18 28 views
6

Jestem całkiem nowy w Javie i próbuję wygenerować zadanie, które będzie uruchamiane co 5 do 10 sekund, więc w dowolnym odstępie czasu w obszarze od 5 do 10, w tym 10.Java: Planowanie zadania w przypadkowych odstępach czasu

Próbowałem kilku rzeczy, ale nic nie działa tak daleko. Mój ostatni wysiłek jest poniżej:

timer= new Timer(); 
Random generator = new Random(); 
int interval; 

//The task will run after 10 seconds for the first time: 
timer.schedule(task, 10000); 

//Wait for the first execution of the task to finish:    
try { 
    sleep(10000); 
} catch(InterruptedException ex) { 
ex.printStackTrace(); 
} 

//Afterwards, run it every 5 to 10 seconds, until a condition becomes true: 
while(!some_condition)){ 
    interval = (generator.nextInt(6)+5)*1000; 
    timer.schedule(task,interval); 

    try { 
     sleep(interval); 
    } catch(InterruptedException ex) { 
    ex.printStackTrace(); 
    } 
} 

"zadanie" to zadanie czasowe. Co pojawia się:

Exception in thread "Thread-4" java.lang.IllegalStateException: Task already scheduled or cancelled 

Rozumiem, że od here TimerTask nie mogą być ponownie wykorzystane, ale nie jestem pewien, jak to naprawić. Przy okazji mój TimerTask jest dość skomplikowany i trwa co najmniej 1,5 sekundy.

Każda pomoc zostanie doceniona, dzięki!

Odpowiedz

12

spróbować

public class Test1 { 
    static Timer timer = new Timer(); 

    static class Task extends TimerTask { 
     @Override 
     public void run() { 
      int delay = (5 + new Random().nextInt(5)) * 1000; 
      timer.schedule(new Task(), delay); 
      System.out.println(new Date()); 
     } 

    } 

    public static void main(String[] args) throws Exception { 
     new Task().run(); 
    } 
} 
+1

Wydaje się działać, dzięki! – menackin

1

Utwórz nowy Timer dla każdego zadania, a nie, jak już zrobić: timer= new Timer();

A jeśli chcesz synchronizować swój kod ze swoich zadań gwintowanych należy użyć semaforów i nie sleep(10000). To może zadziałać, jeśli masz szczęście, ale na pewno jest źle, ponieważ nie możesz być pewny, że zadanie zostało faktycznie zakończone.

+0

Dziękuję za odpowiedź. Mam tylko jedno zadanie, które uruchomi określoną liczbę razy jeden po drugim. Czy myślisz, że nadal potrzebuję semaforów? Ponadto, jeśli utworzę nowy licznik dla każdego uruchomienia zadania, czy to oznacza, że ​​potrzebuję tablicy timerów lub czegoś w tym rodzaju? – menackin

+0

Powiedziałeś, że chcesz poczekać na zakończenie pierwszego zadania. To wymaga semafora. Nie musisz śledzić liczników, jeśli nie chcesz. Zostaną one automatycznie zwolnione później przez GC. – m0skit0