将服务器时间转换为本地时间后得到错误的时间

时间:2018-04-04 14:31:48

标签: android timezone datetime-parsing android-date

我从服务器那里收到这种格式的时间:

  

2018-04-04T08:41:21.265185Z

我已将此时间转换为当地时间。但是在转换之后我得到的时间比目前的时间长一个小时。

这是时间转换的代码:

SimpleDateFormat dateFormat=new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS'Z'");
try {
   Date date=dateFormat.parse(bookingTime);
    TimeZone zone=TimeZone.getTimeZone("IST");
    dateFormat.setTimeZone(zone);
    tempTime=dateFormat.format(date);
    finalTime=tempTime.substring(11,16);
    Log.i("time",finalTime);
    Log.i("timeOriginal",tempTime);
} catch (ParseException e) {
    e.printStackTrace();
}  

如何从转换后的服务器时间减去一小时以获得实际时间?

1 个答案:

答案 0 :(得分:3)

最后Z表示日期/时间is in UTC。当你把它放在引号('Z')中时,你要对格式化程序说它应该被视为文字(字母Z本身),忽略它在UTC中的事实 - 格式化程序将使用JVM默认时区。

另一个细节是你的输入有6位十进制数字表示秒数:

  

2018-04-04T08:41:21的 265185 ž

不幸的是,SimpleDateFormat只能处理3个十进制数字。超过3位数,it gives wrong results

另一种方法是丢弃额外数字,只留下3.然后使用另一个格式化程序获取输出(优于substring):

SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSSXXX");
String input = "2018-04-04T08:41:21.265185Z";
// keep only 3 decimal digits, ignore the rest
input = input.replaceAll("(\\.\\d{3})\\d*", "$1"); // input is now "2018-04-04T08:41:21.265Z"
// parse it
Date date = dateFormat.parse(input);

SimpleDateFormat outputFormat = new SimpleDateFormat("HH:mm");
outputFormat.setTimeZone(TimeZone.getTimeZone("Asia/Kolkata"));
// convert the UTC date to another timezone
String finalTime = outputFormat.format(date); // 14:11

这将UTC的时间(08:41)转换为印度的时区(14:11) - 这就是我从您的问题中理解的,您正在尝试做的事情

对于时区名称,我使用" Asia / Kolkata"。缩写,例如" IST"模棱两可,API通常不能满足您的需求(IST在以色列,爱尔兰和印度使用,谁知道API认为是默认值)。

要解析所有6个小数位数,唯一的方法是使用另一个API。在Android中,您可以在API级别26中使用ThreetenABPjava.time classes

Instant instant = Instant.parse("2018-04-04T08:41:21.265185Z");
String finalTime = instant
    // convert to another timezone
    .atZone(ZoneId.of("Asia/Kolkata"))
    // format (just hour and minutes) -> 14:11
    .format(DateTimeFormatter.ofPattern("HH:mm"));