我有一个以UTC为单位的时间戳,我想在不使用像TimeZone.getTimeZone("PST")
这样的API调用的情况下将其转换为本地时间。你到底该怎么做?我一直在使用以下代码,但没有取得多大成功:
private static final SimpleDateFormat mSegmentStartTimeFormatter = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS");
Calendar calendar = Calendar.getInstance();
try {
calendar.setTime(mSegmentStartTimeFormatter.parse(startTime));
}
catch (ParseException e) {
e.printStackTrace();
}
return calendar.getTimeInMillis();
样本输入值:[2012-08-15T22:56:02.038Z]
应返回等效的[2012-08-15T15:56:02.038Z]
Date
没有时区,内部存储在UTC。只有在格式化日期时,才会应用时区校正。当使用DateFormat
时,它默认为运行JVM的时区。根据需要使用setTimeZone
进行更改。
DateFormat utcFormat = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS'Z'");
utcFormat.setTimeZone(TimeZone.getTimeZone("UTC"));
Date date = utcFormat.parse("2012-08-15T22:56:02.038Z");
DateFormat pstFormat = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS");
pstFormat.setTimeZone(TimeZone.getTimeZone("PST"));
System.out.println(pstFormat.format(date));
这将打印2012-08-15T15:56:02.038
注意,我在PST格式中省略了'Z'
,因为它表示UTC。如果你只使用Z
,那么输出将是2012-08-15T15:56:02.038-0700
使用现代Java日期&时间API,这很简单:
String inputValue = "2012-08-15T22:56:02.038Z";
Instant timestamp = Instant.parse(inputValue);
ZonedDateTime losAngelesTime = timestamp.atZone(ZoneId.of("America/Los_Angeles"));
System.out.println(losAngelesTime);
这将打印
2012-08-15T15:56:02.038-07:00[America/Los_Angeles]
注意事项:
- 你的期望值中有一个小错误。时间戳中的
Z
表示UTC,也称为祖鲁时间。因此,在您的本地时间值中,Z
不应该存在。相反,您想要一个返回值,例如2012-08-15T15:56:02.038-07:00
,因为偏移量现在是-7小时而不是Z - 避免使用三个字母的时区缩写。它们不是标准化的,因此常常含糊不清。例如,PST可能意味着费城标准时间、太平洋标准时间或皮特凯恩标准时间(尽管缩写中的S通常表示夏令时间(意为夏令时))。如果你打算使用太平洋标准时间,那甚至不是一个时区,因为在夏天(你的样本时间戳所在的地方)会使用太平洋夏令时。在我的代码中,使用地区/城市格式的时区ID,而不是缩写
- 时间戳通常最好作为
Instant
对象来处理。只有在您有需要时,如演示时,才转换为ZonedDateTime
问题:我可以在我的Java版本中使用现代API吗
如果至少使用Java6,则可以。
- 在Java 8和更高版本中,新的API是内置的
- 在Java6和7中,获得ThreeTen Backport,即新类的后端口(这是JSR-310的ThreeTen,现代API是在这里首次定义的)
- 在Android上,使用Android版的ThreeTen Backport。它被称为ThreeTenABP,我认为这个问题有一个很好的解释:如何在Android项目中使用ThreeTenaABP
Instant timestamp = Instant.parse("2023-07-25T11:04:31.650Z");
System.out.println(timestamp.atZone(ZoneId.systemDefault()).toOffsetDateTime());
打印我的位置:
2023-07-25T13:04:31.650+02:00
这是一个简单的改进解决方案
public String convertToCurrentTimeZone(String Date) {
String converted_date = "";
try {
DateFormat utcFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
utcFormat.setTimeZone(TimeZone.getTimeZone("UTC"));
Date date = utcFormat.parse(Date);
DateFormat currentTFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
currentTFormat.setTimeZone(TimeZone.getTimeZone(getCurrentTimeZone()));
converted_date = currentTFormat.format(date);
}catch (Exception e){ e.printStackTrace();}
return converted_date;
}
//get the current time zone
public String getCurrentTimeZone(){
TimeZone tz = Calendar.getInstance().getTimeZone();
System.out.println(tz.getDisplayName());
return tz.getID();
}