我正在制作一个可在用户输入位置并退出时保存的应用。我必须为此分隔Date
个对象。当我打印出值时,它们会返回相同的确切时间,尽管它们会在不同的时间保存。可能导致这种情况的任何想法?
我的 checkLocation()方法:
private void checkLocation() {
float[] distance = new float[2];
for(int i = 1; i <= AssetLoader.getTotalLocations(); i++) {
float mItemLat = AssetLoader.getItemLatitude(String.valueOf(i));
float mItemLong = AssetLoader.getItemLongitude(String.valueOf(i));
Location.distanceBetween(mLastLocation.getLatitude(), mLastLocation.getLongitude(),
mItemLat, mItemLong, distance);
if(distance[0] > 55){
Toast.makeText(getBaseContext(), "Outside, distance from center: " + distance[0] + " radius: " + "55", Toast.LENGTH_LONG).show();
if(startDate != null) {
stopDate = calendar.getTime();
Log.e("STOP DATE", "SAVED");
saveTimeDifference(startDate, stopDate, String.valueOf(i));
}
} else {
Toast.makeText(getBaseContext(), "Inside, distance from center: " + distance[0] + " radius: " + "55", Toast.LENGTH_LONG).show();
if(startDate == null) {
startDate = calendar.getTime();
Log.e("START DATE", "SAVED");
}
}
}
}
计算时差和其他内容时:
public static void saveTimeDifference(Date startDate, Date endDate, String id) {
//TODO: FIX THIS
//milliseconds
long difference = endDate.getTime() - startDate.getTime();
AssetLoader.setItemTimeDifference(id, difference);
System.out.println("startDate : " + startDate);
System.out.println("endDate : "+ endDate);
System.out.println("difference : " + difference);
long secondsInMilli = 1000;
long minutesInMilli = secondsInMilli * 60;
long hoursInMilli = minutesInMilli * 60;
long daysInMilli = hoursInMilli * 24;
long elapsedDays = difference / daysInMilli;
difference = difference % daysInMilli;
long elapsedHours = difference / hoursInMilli;
difference = difference % hoursInMilli;
long elapsedMinutes = difference / minutesInMilli;
difference = difference % minutesInMilli;
long elapsedSeconds = difference / secondsInMilli;
Log.e("saveTimeDifference()", elapsedDays + " days, " + elapsedHours + " hours, " + elapsedMinutes + " minutes, " + elapsedSeconds + " seconds");
AssetLoader.setItemDetails(AssetLoader.getItemName(String.valueOf(id)), AssetLoader.getItemDetails(AssetLoader.getItemName(String.valueOf(id))) + "\nStart Date: " + startDate + " Stop Date: " + startDate);
}
请注意在不同时间访问当前时间。在GregorianCalendar对象上调用getTime()时似乎保存错误或返回错误的时间。
感谢您的任何建议!
答案 0 :(得分:7)
calendar.getTime()
返回当前存储在java.util.Date
对象中的Calendar
个对象。
当最初通过调用Calendar.getInstance()
(或其他方式)获得Calendar
时,它具有“当前时间”。
5小时后仍然会有同样的时间。这不是“实时”时间,因此对calendar.getTime()
的多次调用将获得相同的值。
如果您想捕获当前时间,请致电new Date()
:
Date startDate = new Date();
// do work
Date stopDate = new Date();
long difference = endDate.getTime() - startDate.getTime();
System.out.println("Work took " + difference + "ms");
答案 1 :(得分:2)
accepted Answer by Andreas是正确的。
如果您正在进行更多的日期工作,请考虑使用新的java.time框架,该框架取代了麻烦的旧日期时间类。
要获取UTC中时间轴上的当前时刻,其分辨率最高为nanoseconds,请使用Instant
。
Instant now = Instant.now();
java.time中的类使用Immutable Objects模式。每个实例的值永远不会改变(从不“改变”)。因此,当您想要再次了解当前时刻时,再次致电Instant.now
以创建另一个Instant
实例。
在Java 8中,当前时刻的分辨率最高为milliseconds,而不是类的处理能力nanoseconds。此限制是由于使用Clock
的遗留实现。在Java 9中,Clock
的新实现根据计算机的硬件时钟捕获最高达纳秒分辨率的当前时刻。
虽然通常最好将日期时间值存储在UTC中,但对于演示文稿,您可能希望在用户期望的时区中显示值。
要将Instant
调整为特定wall-clock time,请应用时区(ZoneId
)。指定proper time zone name,不要使用EST
或IST
之类的3-4个字母缩写。
ZoneId zoneId = ZoneId.of( "America/Montreal" );
ZonedDateTime zdt = ZonedDateTime.ofInstant( now , zoneId );
要按天 - 小时 - 分钟 - 秒跟踪经过的时间跨度,请使用Duration
课程。作为文本表示,此类使用标准ISO 8601格式(例如PT1H30M
)解析并生成字符串一个半小时。
Duration duration = Duration.between( startInstant , stopInstant );
String output = duration.toString();
您可以在这段时间内获得纳秒或秒或分钟或小时或天的总数。
奇怪的是,Java 8中的Duration
类缺少方便地查询日期部分,小时部分,分钟部分和秒部分的方法。 Java 9 brings such methods
对于几年 - 几天的时间跨度,请使用Period
类。