Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/321.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 日期到日期的转换_Java_Datetime_Simpledateformat_Epoch_Datetime Parsing - Fatal编程技术网

Java 日期到日期的转换

Java 日期到日期的转换,java,datetime,simpledateformat,epoch,datetime-parsing,Java,Datetime,Simpledateformat,Epoch,Datetime Parsing,我想将2018-02-21 15:47:35UTC转换为历代UTC格式。我们怎么做?我目前在PST SimpleDateFormat df = new SimpleDateFormat("YYYY-MM-DD HH:MM:SS"); df.setTimeZone(TimeZone.getTimeZone("UTC")); date = df.parse(dateString).getTime(); 上面的代码应该返回自1970年1月1日00:00:00 GMT以来的毫秒数,但我得到的值不正确

我想将
2018-02-21 15:47:35
UTC转换为历代UTC格式。我们怎么做?我目前在PST

SimpleDateFormat df = new SimpleDateFormat("YYYY-MM-DD HH:MM:SS");

df.setTimeZone(TimeZone.getTimeZone("UTC"));
date = df.parse(dateString).getTime();

上面的代码应该返回自1970年1月1日00:00:00 GMT以来的毫秒数,但我得到的值不正确。

您的代码唯一的问题是DateFormat

请查收。

我在PKT,所以输出会有所不同

1519228055000
Wed Feb 21 20:47:35 PKT 2018
Wed Feb 21 20:47:35 PKT 2018

代码的唯一问题是日期格式

请查收。

我在PKT,所以输出会有所不同

1519228055000
Wed Feb 21 20:47:35 PKT 2018
Wed Feb 21 20:47:35 PKT 2018

也可以通过java8时间库完成:

String dateString = "2018-02-21 15:47:35";

DateTimeFormatter dateTimeFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss", Locale.ENGLISH);

dateTimeFormatter.withZone(ZoneId.of("UTC"));
LocalDateTime parsedDateTime = LocalDateTime.from(dateTimeFormatter.parse(dateString));
ZonedDateTime timeAtYourZone = parsedDateTime.atZone(ZoneId.systemDefault());

System.out.println(timeAtYourZone.toInstant().toEpochMilli());
System.out.println(timeAtYourZone);

也可以通过java8时间库完成:

String dateString = "2018-02-21 15:47:35";

DateTimeFormatter dateTimeFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss", Locale.ENGLISH);

dateTimeFormatter.withZone(ZoneId.of("UTC"));
LocalDateTime parsedDateTime = LocalDateTime.from(dateTimeFormatter.parse(dateString));
ZonedDateTime timeAtYourZone = parsedDateTime.atZone(ZoneId.systemDefault());

System.out.println(timeAtYourZone.toInstant().toEpochMilli());
System.out.println(timeAtYourZone);

您的模式必须是
yyyy-MM-dd HH:MM:ss
,其他答案告诉您:

SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
我只想补充一些细节

首先,看看javadoc中的模式描述:

请注意,小写的y与大写的y不同(小写是年份,而大写是-2个定义完全不同的字段)

还请注意,大写的D是一年中的一天,而月份的一天(这是您想要的)是小写的D。大写字母M表示月份,小写字母M表示小时分钟

大写的S是毫秒字段,而秒由小写的S表示

simpleDataFormat
的设计也没有帮助:该类只是尝试解析字符串,即使month字段(MM)在模式中出现两次,而minutes字段却没有出现(并且它被设置为默认值零-全部在幕后,没有任何警告,没有任何错误指示)

结论:始终阅读文档:-)

对于java 8或更高,考虑使用新的日期API,这是更好的,因为它没有所有这些幕后的东西:

DateTimeFormatter fmt = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")
                           .withZone(ZoneOffset.UTC);
long epochMilli = Instant.from(fmt.parse("2018-02-21 15:47:35")).toEpochMilli();

如果您使用类似于
YYYY-MM-DD HH:MM:SS
的模式,此API也将引发异常,因为它将尝试将分钟值47解析为一个月(因为大写字母MM将位于相应的位置),而47不是有效的月份。

您的模式必须是
yyy-MM-DD HH:MM:SS
,正如其他答案告诉你的:

SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
我只想补充一些细节

首先,看看javadoc中的模式描述:

请注意,小写的y与大写的y不同(小写是年份,而大写是-2个定义完全不同的字段)

还请注意,大写的D是一年中的一天,而月份的一天(这是您想要的)是小写的D。大写字母M表示月份,小写字母M表示小时分钟

大写的S是毫秒字段,而秒由小写的S表示

simpleDataFormat
的设计也没有帮助:该类只是尝试解析字符串,即使month字段(MM)在模式中出现两次,而minutes字段却没有出现(并且它被设置为默认值零-全部在幕后,没有任何警告,没有任何错误指示)

结论:始终阅读文档:-)

对于java 8或更高,考虑使用新的日期API,这是更好的,因为它没有所有这些幕后的东西:

DateTimeFormatter fmt = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")
                           .withZone(ZoneOffset.UTC);
long epochMilli = Instant.from(fmt.parse("2018-02-21 15:47:35")).toEpochMilli();

如果使用类似于
YYYY-MM-DD HH:MM:SS
的模式,此API也将引发异常,因为它将尝试将分钟值47解析为一个月(因为大写字母MM将位于相应的位置),而47不是有效月份。

预期的:2018-02-21 15:47:35 UTC相当于自1970年1月1日0:00 UTC以来的1519 228 055 000毫秒

观察到的:问题中的代码给出1514 818 800 035。所以它是4409254965毫秒,51天多一点

解决方案

    DateTimeFormatter dtf = DateTimeFormatter.ofPattern("uuuu-MM-dd HH:mm:ss");
    date = LocalDateTime.parse("2018-02-21 15:47:35", dtf)
            .atOffset(ZoneOffset.UTC)
            .toInstant()
            .toEpochMilli();
这给出了正确的1519228 055000

出了什么问题?

SimpleDateFormat
的许多麻烦特性之一是,在默认设置下,如果指定了错误的格式模式字符串,它通常会给出错误的结果,并假装一切正常。我在我的代码片段中使用的现代Java日期和时间API,正试图更努力地找出模式什么时候没有意义,并告诉您它是错误的。例如,让我们使用现代的
DateTimeFormatter
,尝试您的格式模式:

    final DateTimeFormatter dtf = DateTimeFormatter.ofPattern("YYYY-MM-DD HH:MM:SS");
    LocalDateTime.parse(dateString, dtf);
这将抛出一个
java.time.format.DateTimeParseException:无法在索引14处解析文本“2018-02-21 15:47:35”。索引14是字符串中47的位置,应该是分钟数。显然47与格式中的
MM
不匹配。如果您还没有弄明白,请查看文档。它说大写的
M
表示“一年中的一个月”。因此,格式化程序试图告诉您的是,一年中没有47个月。在文档中,您还可以找到表示“小时分钟”的小写字母
m
。当您更正格式模式字符串中字母的大小写时,您将收到其他异常,直到最后出现
yyyy-MM-dd HH:MM:ss
uuu-MM-dd HH:MM:ss
(小写
yyyy
是年份或纪元,
uuuu
是签名年份,两者都在第0年之后的年份有效)

链接

  • 解释如何使用
    java.time
  • 拼写格式模式字符串的大小写字母

预计:2018-02-21 15:47:35 UTC相当于1519 228 055 000 mill