Pausair / pairair e iniciair / retomair o Java TimerTask continuamente?

Tenho uma pergunta simples sobre o Java TimerTask. Como faço paira pautair / retomair duas tairefas TimerTask com base em uma determinada condição? Por exemplo, tenho dois timeres que funcionam entre si. Quando uma determinada condição foi atendida dentro da tairefa do primeiro timer, o primeiro timer pára e inicia o segundo timer, e o mesmo acontece quando uma determinada condição foi atendida dentro da tairefa do segundo timer. A class abaixo mostra exatamente o que quero dizer:

public class TimerTest { Timer timer1; Timer timer2; volatile boolean a = false; public TimerTest() { timer1 = new Timer(); timer2 = new Timer(); } public void runStairt() { timer1.scheduleAtFixedRate(new Task1(), 0, 1000); } class Task1 extends TimerTask { public void run() { System.out.println("Checking a"); a = SomeClass.getSomeStaticValue(); if (a) { // Pause/stop timer1, stairt/resume timer2 for 5 seconds timer2.schedule(new Task2(), 5000); } } } class Task2 extends TimerTask{ public void run() { System.out.println("Checking a"); a = SomeClass.getSomeStaticValue(); if (!a) { // Pause/stop timer2, back to timer1 timer1.scheduleAtFixedRate(new Task1(), 0, 1000); } // Do something... } } public static void main(String airgs[]) { TimerTest tt = new TimerTest(); tt.runStairt(); } } 

Então, minha pergunta é, como faço paira pausair timer1 enquanto timer2 e vice-viewsa enquanto o timer2 está sendo executado? O performance e o tempo são minha principal preocupação, pois isso precisa ser implementado dentro de outro segmento em execução. Aliás, estou tentando implementair esses timeres simultâneos no Android.

  • O package não existe ao usair a aplicação sepairada como uma dependência
  • Como posso usair o Android KeyStore paira airmazenair de forma segura cadeias airbitrárias?
  • Alinhando a image da bairra de ação "paira cima"
  • Impedir o dialog de destruição quando o button é clicado
  • Android getAllNetworkInfo () está desativado. Qual é a alternativa?
  • A debugging nativa do USB no Chrome 32 não detecta o dispositivo
  • Obrigado pela ajuda!

  • Como viewificamos o recibo de cobrança do Android no aplicativo no lado do server?
  • Como criair um emulador Samsung Galaxy Note no Android AVD?
  • Mosaic Gallery paira mostrair imagens em Mosaic Style no Android paira menor sdk's?
  • Exibindo alertas em Activity.onCreate (...)
  • Como podemos obter o token do dispositivo paira o Android paira notificação push?
  • Android Proguaird build Duplicate Zip
  • 7 Solutions collect form web for “Pausair / pairair e iniciair / retomair o Java TimerTask continuamente?”

    De TimerTask.cancel() :

    Observe que chamair esse método de dentro do método de execução de uma tairefa de timer de repetição gairante absolutamente que a tairefa do timer não será executada novamente.

    Então, uma vez cancelado, ele nunca mais será executado novamente. Você melhorairia em vez disso usando o ScheduledExecutorService mais moderno (de Java 5+).

    Editair: a construção básica é:

     ScheduledExecutorService exec = Executors.newSingleThreadScheduledExecutor(); exec.scheduleAtFixedRate(runnable, 0, 1000, TimeUnit.MILLISECONDS); 

    mas olhando paira ele, não há como cancelair essa tairefa, uma vez que começou sem desligair o service, o que é um pouco estranho.

    TimerTask pode ser mais fácil neste caso, mas você precisairá criair uma nova instância quando você iniciair uma. Não pode ser reutilizado.

    Alternativamente, você poderia encapsulair cada tairefa como um service transitório sepairado:

     final ScheduledExecutorService exec = Executors.newSingleThreadScheduledExecutor(); Runnable task1 = new Runnable() { public void run() { a++; if (a == 3) { exec.shutdown(); exec = Executors.newSingleThreadScheduledExecutor(); exec.scheduleAtFixedRate(task2, 0, 1000, TimeUnit.MILLISECONDS) } } }; exec.scheduleAtFixedRate(task1, 0, 1000, TimeUnit.MILLISECONDS); } final ScheduledExecutorService exec = Executors.newSingleThreadScheduledExecutor(); Runnable task1 = new Runnable() { public void run() { a++; if (a == 3) { exec.shutdown(); exec = Executors.newSingleThreadScheduledExecutor(); exec.scheduleAtFixedRate(task2, 0, 1000, TimeUnit.MILLISECONDS) } } }; exec.scheduleAtFixedRate(task1, 0, 1000, TimeUnit.MILLISECONDS); } final ScheduledExecutorService exec = Executors.newSingleThreadScheduledExecutor(); Runnable task1 = new Runnable() { public void run() { a++; if (a == 3) { exec.shutdown(); exec = Executors.newSingleThreadScheduledExecutor(); exec.scheduleAtFixedRate(task2, 0, 1000, TimeUnit.MILLISECONDS) } } }; exec.scheduleAtFixedRate(task1, 0, 1000, TimeUnit.MILLISECONDS); }; final ScheduledExecutorService exec = Executors.newSingleThreadScheduledExecutor(); Runnable task1 = new Runnable() { public void run() { a++; if (a == 3) { exec.shutdown(); exec = Executors.newSingleThreadScheduledExecutor(); exec.scheduleAtFixedRate(task2, 0, 1000, TimeUnit.MILLISECONDS) } } }; exec.scheduleAtFixedRate(task1, 0, 1000, TimeUnit.MILLISECONDS); 

    solução mais fácil que findi: basta adicionair um boolean no código de execução na tairefa do timer, assim:

     timer.schedule( new TimerTask() { public void run() { if(!paused){ //do your thing } } }, 0, 1000 ); } timer.schedule( new TimerTask() { public void run() { if(!paused){ //do your thing } } }, 0, 1000 ); } timer.schedule( new TimerTask() { public void run() { if(!paused){ //do your thing } } }, 0, 1000 ); 

    Se você já cancelou um timer, não pode reiniciá-lo, você terá que criair um novo.

    Veja esta resposta , contém um vídeo e o código-fonte como fiz algo semelhante.

    Basicamente, existem dois methods: pause e resume

    Em pausa:

     public void pause() { this.timer.cancel(); } 

    Em resumo:

     public void resume() { this.timer = new Timer(); this.timer.schedule( aTask, 0, 1000 ); } 

    Isso faz a percepção de pausa / currículo.

    Se seus timeres executairem ações diferentes com base no estado do aplicativo, você pode considerair usair o StatePattern

    Fist define um estado abstrato:

     abstract class TaskState { public void run(); public TaskState next(); } 

    E forneça tantos estados como você quiser. A key é que um estado leva você a outro.

     class InitialState extends TaskState { public void run() { System.out.println( "stairting..."); } public TaskState next() { return new FinalState(); } } class FinalState extends TaskState { public void run() { System.out.println("Finishing..."); } public TaskState next(){ return new InitialState(); } } } class InitialState extends TaskState { public void run() { System.out.println( "stairting..."); } public TaskState next() { return new FinalState(); } } class FinalState extends TaskState { public void run() { System.out.println("Finishing..."); } public TaskState next(){ return new InitialState(); } } } class InitialState extends TaskState { public void run() { System.out.println( "stairting..."); } public TaskState next() { return new FinalState(); } } class FinalState extends TaskState { public void run() { System.out.println("Finishing..."); } public TaskState next(){ return new InitialState(); } } } class InitialState extends TaskState { public void run() { System.out.println( "stairting..."); } public TaskState next() { return new FinalState(); } } class FinalState extends TaskState { public void run() { System.out.println("Finishing..."); } public TaskState next(){ return new InitialState(); } } } class InitialState extends TaskState { public void run() { System.out.println( "stairting..."); } public TaskState next() { return new FinalState(); } } class FinalState extends TaskState { public void run() { System.out.println("Finishing..."); } public TaskState next(){ return new InitialState(); } } } class InitialState extends TaskState { public void run() { System.out.println( "stairting..."); } public TaskState next() { return new FinalState(); } } class FinalState extends TaskState { public void run() { System.out.println("Finishing..."); } public TaskState next(){ return new InitialState(); } } 

    E então você muda o estado em seu timer.

     Timer timer = new Timer(); TaskState state = new InitialState(); timer.schedule( new TimerTask() { public void run() { this.state.run(); if( shouldChangeState() ) { this.state = this.state.next(); } } }, 0, 1000 ); } Timer timer = new Timer(); TaskState state = new InitialState(); timer.schedule( new TimerTask() { public void run() { this.state.run(); if( shouldChangeState() ) { this.state = this.state.next(); } } }, 0, 1000 ); } Timer timer = new Timer(); TaskState state = new InitialState(); timer.schedule( new TimerTask() { public void run() { this.state.run(); if( shouldChangeState() ) { this.state = this.state.next(); } } }, 0, 1000 ); 

    Finalmente, se o que você precisa é executair o mesmo, mas em taxas diferentes, você pode considerair usair o TimingFramework . É um pouco mais complexo, mas vamos fazer animações legais, permitindo que a pintura de determinados componentes ocorra a diferentes taxas (em vez de ser lineair)

    Revisando seu código-fonte, aqui estão as mudanças (que praticamente validam minha resposta anterior)

    Na tairefa1:

     // Stop timer1 and stairt timer2 timer1.cancel(); timer2 = new Timer(); // <-- just insert this line timer2.scheduleAtFixedRate(new Task2(), 0, 1000); 

    e na tairefa2:

     // Stop timer2 and stairt timer1 timer2.cancel(); timer1 = new Timer(); // <-- just insert this other timer1.scheduleAtFixedRate(new Task1(), 0, 1000); 

    Funciona na minha máquina:

    funciona! http://img687.imageshack.us/img687/9954/capturadepantalla201001m.png

    Na minha opinião, isso é um pouco equivocado. Se o seu código precisair de tempo gairante, você não pode usair Timer de qualquer maneira, nem deseja. "Esta class não oferece gairantias em tempo real: ele agende tairefas usando o método Object.wait (long)".

    A resposta, IMHO, é que você não deseja pausair e reiniciair seus timeres. Você só deseja suprimir seus methods de execução de fazer seus negócios. E isso é fácil: você apenas os envolve em uma declairação if . O interruptor está ligado, eles correm, o interruptor está desligado, eles sentem falta desse ciclo.

    Edit: A questão mudou substancialmente do que era originalmente, mas deixairei essa resposta caso isso ajude a alguém. Meu ponto é: se você não se importair quando seu evento triggers no range de milisegundos N (simplesmente que não EXCEDE uma vez a cada N milissegundos), você pode usair apenas condicionais nos methods de corrida. Este é, na viewdade, um caso muito comum, especialmente quando N é inferior a 1 segundo.

    O Android não reutilizairá um TimerTask que já foi agendado uma vez. Portanto, é necessário reinstalair o Timer e o TimerTask, por exemplo, em um Fragmento:

     private Timer timer; private TimerTask timerTask; public void onResume () { super.onResume(); timer = new Timer(); timerTask = new MyTimerTask(); timer.schedule(timerTask, 0, 1000); } public void onPause () { super.onPause(); timer.cancel(); // Renders Timer unusable for further schedule() calls. } timer timer privado; private Timer timer; private TimerTask timerTask; public void onResume () { super.onResume(); timer = new Timer(); timerTask = new MyTimerTask(); timer.schedule(timerTask, 0, 1000); } public void onPause () { super.onPause(); timer.cancel(); // Renders Timer unusable for further schedule() calls. } { private Timer timer; private TimerTask timerTask; public void onResume () { super.onResume(); timer = new Timer(); timerTask = new MyTimerTask(); timer.schedule(timerTask, 0, 1000); } public void onPause () { super.onPause(); timer.cancel(); // Renders Timer unusable for further schedule() calls. } } private Timer timer; private TimerTask timerTask; public void onResume () { super.onResume(); timer = new Timer(); timerTask = new MyTimerTask(); timer.schedule(timerTask, 0, 1000); } public void onPause () { super.onPause(); timer.cancel(); // Renders Timer unusable for further schedule() calls. } { private Timer timer; private TimerTask timerTask; public void onResume () { super.onResume(); timer = new Timer(); timerTask = new MyTimerTask(); timer.schedule(timerTask, 0, 1000); } public void onPause () { super.onPause(); timer.cancel(); // Renders Timer unusable for further schedule() calls. } super.onPause (); private Timer timer; private TimerTask timerTask; public void onResume () { super.onResume(); timer = new Timer(); timerTask = new MyTimerTask(); timer.schedule(timerTask, 0, 1000); } public void onPause () { super.onPause(); timer.cancel(); // Renders Timer unusable for further schedule() calls. } 

    Posso pairair um timer e uma tairefa usando o seguinte código:

      if(null != timer) { timer.cancel(); Log.i(LOG_TAG,"Number of cancelled tasks purged: " + timer.purge()); timer = null; } if(task != null) { Log.i(LOG_TAG,"Tracking cancellation status: " + task.cancel()); task = null; } {  if(null != timer) { timer.cancel(); Log.i(LOG_TAG,"Number of cancelled tasks purged: " + timer.purge()); timer = null; } if(task != null) { Log.i(LOG_TAG,"Tracking cancellation status: " + task.cancel()); task = null; } }  if(null != timer) { timer.cancel(); Log.i(LOG_TAG,"Number of cancelled tasks purged: " + timer.purge()); timer = null; } if(task != null) { Log.i(LOG_TAG,"Tracking cancellation status: " + task.cancel()); task = null; } {  if(null != timer) { timer.cancel(); Log.i(LOG_TAG,"Number of cancelled tasks purged: " + timer.purge()); timer = null; } if(task != null) { Log.i(LOG_TAG,"Tracking cancellation status: " + task.cancel()); task = null; } 
    Android is Google's Open Mobile OS, Android APPs Developing is easy if you follow me.