2015-02-03 3 views
3

나는 타이머를 예약하고있는 게임을 가지고있다. 플레이어가 로그 아웃 및 서버가 재부팅 된 경우 CoresManager 타이머 실행이 중지타이머가 실행 중인지 확인하는 코드가 있습니까?

private void startTimer() { 
    CoresManager.fastExecutor.scheduleAtFixedRate(new TimerTask() { 
     @Override 
     public void run() { 
      if (timer == 0 || timer < 1) { 
       player.sm("Your timer has ended! The NPCs will no longer spawn."); 
       timer = 0; 
       this.cancel(); 
       exitInstance(); 
       return; 
      } 
      timer--; 
      timerchecker = true; 
      seconds = timer % 60; 
      player.setTimer(timer); 
      minutes = TimeUnit.SECONDS.toMinutes(timer);    
     } 
    }, 0, 1000); 
} 

: 나는 게임 내에서이를 사용하고

package com.rs.cores; 

import java.util.Timer; 
import java.util.concurrent.ExecutorService; 
import java.util.concurrent.Executors; 
import java.util.concurrent.ScheduledExecutorService; 

public final class CoresManager { 

protected static volatile boolean shutdown; 
public static WorldThread worldThread; 
public static ExecutorService serverWorkerChannelExecutor; 
public static ExecutorService serverBossChannelExecutor; 
public static Timer fastExecutor; 
public static ScheduledExecutorService slowExecutor; 
public static int serverWorkersCount; 

public static void init() { 
    worldThread = new WorldThread(); 
    int availableProcessors = Runtime.getRuntime().availableProcessors(); 
    serverWorkersCount = availableProcessors >= 6 ? availableProcessors - (availableProcessors >= 12 ? 7 : 5) : 1; 
    serverWorkerChannelExecutor = availableProcessors >= 6 ? Executors 
      .newFixedThreadPool(availableProcessors - (availableProcessors >= 12 ? 7 : 5), 
      new DecoderThreadFactory()) : Executors.newSingleThreadExecutor(new DecoderThreadFactory()); 
    serverBossChannelExecutor = Executors 
      .newSingleThreadExecutor(new DecoderThreadFactory()); 
    fastExecutor = new Timer("Fast Executor"); 
    slowExecutor = availableProcessors >= 6 ? Executors.newScheduledThreadPool(availableProcessors >= 12 ? 4 : 2, 
        new SlowThreadFactory()) : Executors 
      .newSingleThreadScheduledExecutor(new SlowThreadFactory()); 
    worldThread.start(); 
} 

public static void shutdown() { 
    serverWorkerChannelExecutor.shutdown(); 
    serverBossChannelExecutor.shutdown(); 
    fastExecutor.cancel(); 
    slowExecutor.shutdown(); 
    shutdown = true; 
} 

private CoresManager() { 

} 
} 

:이 CoresManager 파일이 있습니다. 다시 실행하려면 다시 로그인하면 startTimer()를 다시 수행하도록 코드를 추가했습니다. 그러나 서버가 로그 아웃하지 않으면 타이머가 계속 실행되므로 타이머가 두 번 실행되기 시작합니다. 타이머는 로그 아웃 한 횟수에 따라 2 또는 그 이상을 뺍니다. 타이머가 이미 실행 중인지 확인하기위한 코드가 있으면 문제가 해결 될 것이라고 생각합니다. 이것을 할 수있는 방법이 있습니까? 도와주세요!

답변

6

TimerTask 개체 (http://docs.oracle.com/javase/1.5.0/docs/api/java/util/TimerTask.html)의 상태를 검사 할 수있는 설명서에는 아무것도 표시되지 않으므로 TimerTask를 확장하고 자신 만의 클래스를 만드는 것이 좋습니다. 대신 익명의 TimerTask를 사용하여, 당신은의 라인을 따라 뭔가 만들 수 있습니다

public class CoresTimerTask extends TimerTask { 

    private boolean hasStarted = false; 

    @Overrides 
    public void run() { 
     this.hasStarted = true; 
     //rest of run logic here... 
    } 

    public boolean hasRunStarted() { 
     return this.hasStarted; 
    } 
} 

을하고 당신이 다음()가 startTimer에 합격이 CoresTimerTask 개체에 대한 참조를 유지합니다. 그런 다음 나중에 hasRunStarted를 통해이 객체를 확인할 수 있습니다.

0

공공 긴 scheduledExecutionTime()이

이 작업의 최근 실제 실행의 예약 된 실행 시간을 돌려줍니다. (태스크 실행이 진행되는 동안이 메소드가 호출되면 반환 값은 진행중인 태스크의 예정된 실행 시간입니다.

이 메소드는 일반적으로 실행되지 않습니다. 예정된 실행 시간이 시간이 지남에 표류 수, 그래서 정말 중요하지 않은대로 고정 지연 실행이 작업을 반복와 함께 사용.

  1. 먼저 주기적으로 실행 작업 상태 플래그
  2. 을 설정/리셋 필요
  3. 초 (예제를 볼 때)이 유형의 클 래스를 봉인하는 것이 좋습니다 의

하지만 누군가가 이러한 방법

 public abstract class NonInterruptableTask extends TimerTask { 
     protected boolean isDone = false; 
     public boolean isDone() {return isDone; } 
     protected abstract void doTaskWord(); 

     @Override 
     public void run() { 
      isDone = false; 
      doTaskWord(); 
      isDone = true; 
     } 

    } 


    TimerTask myTask = new NonInterruptableTask() { 

     @Override 
     public void doTimerWork() { 

      //job here 
     } 
    }; 
을 가지고 주장하는 경우
관련 문제