我正在使用Java,我正在制作游戏。在这个游戏中,实时是非常重要的一部分。 出于这个原因,我试图使用Ntp获得实时。
我在网上找到的是这段代码。
import java.net.InetAddress;
import java.util.Date;
import org.apache.commons.net.ntp.NTPUDPClient;
import org.apache.commons.net.ntp.TimeInfo;
public class test{
public static void main(String args[]) throws Exception{
String TIME_SERVER = "time-a.nist.gov";
NTPUDPClient timeClient = new NTPUDPClient();
InetAddress inetAddress = InetAddress.getByName(TIME_SERVER);
TimeInfo timeInfo = timeClient.getTime(inetAddress);
long returnTime = timeInfo.getReturnTime();
Date time = new Date(returnTime);
System.out.println("Time from " + TIME_SERVER + ": " + time);
}
}
我的问题是使用这个,系统仍然得到System.currentMillis();因为它实际上会打印出本地机器获取时间消息的时间。因此,如果玩家将桌面时间改为未来,游戏时间也会发生变化。
如果有人可以提供实时帮助,我会非常感激。 附:我没有服务器,我的游戏将在Kongregate上播放,数据将在播放器计算机上播放。
提前致谢。
答案 0 :(得分:5)
只需在程序开始时通过NTP获取一次,然后使用System.nanoTime()获取之后的相对时间。它完全是单调的,不会通过设置系统时间来改变。
答案 1 :(得分:3)
根据NTPUDPClient
javadoc:
要使用该类,只需打开一个打开的本地数据报套接字并调用
getTime()
来检索时间。然后调用close以正确关闭连接。允许连续调用getTime而无需重新建立连接。
您在代码中错过了对open()
的来电(技术上close()
),但这不是您发出问题的原因。
此外,在您的要求中,您声明您需要实时(而不是本地客户端可以设置的任何时间)。此数量不应直接获得,而应作为通过方法getOffset()
获得的本地时间与服务器(远程)时间匹配所需的偏移量。
如果获得实时是一个常见的过程,您可能只想在开始时使用NTP一次,并使用获得的偏移来纠正未来的系统时间,从而减少实时检索时的延迟。
这样的过程可以在类中描述:
public class TimeKeeper{
// Constant: Time Server
private final String TIME_SERVER = "time-a.nist.gov";
// Last time the time offset was retrieved via NTP
private long last_offset_time = -1;
// The real time, calculated from offsets, of when the last resync happened
private long retrieve_time;
private synchronized void resync(){
NTPUDPClient timeClient = new NTPUDPClient();
InetAddress inetAddress = InetAddress.getByName(TIME_SERVER);
TimeInfo timeInfo = null;
try{
timeClient.open();
timeInfo = timeClient.getTime(inetAddress);
}catch(IOException ex){
return;
}finally{
timeClient.close();
}
// Real time calculated from the offset time and the current system time.
retrieve_time = System.currentTimeMillis() + timeInfo.getOffset();
last_offset_time = System.nanoTime();
}
public long getRealTimeInMillis(){
// Possible to set some resync criteria here
if(last_offset_time == -1){
resync();
// Handle exception whilst retrieving time here
}
// Returns the system time, corrected with the offset
return retrieve_time + Math.round((System.nanoTime() - last_offset_time) / 1000.0)
}
}
答案 2 :(得分:2)
试试这个:
String TIME_SERVER = "time-a.nist.gov";
TimeTCPClient client = new TimeTCPClient();
try {
client.connect(TIME_SERVER);
System.out.println(client.getDate());
} finally {
client.disconnect();
}