当前位置: 首页 > 知识库问答 >
问题:

Java-用于以毫秒为单位返回纪元时间的简单数据格式格式化程序[重复]

万俟靖
2023-03-14

一般来说,我对Java和编码非常陌生——我有一些代码,它以下面的格式返回时间戳。MM.dd HH:mm:ss:ms,如下所示:

SimpleDateFormat formatter = new SimpleDateFormat("yyyy.MM.dd HH:mm:ss:sss");

这将返回:

2017.07.19 11:42:30:423

是否有一种方法可以编辑上面的“简单数据格式格式化程序”代码,以将日期/时间作为包括毫秒的纪元时间戳返回,以便返回的值按照下面的格式设置?

1500464550423

我希望我可以修改SimpleDateFormat格式化程序代码的(“yyyy.MM.dd HH:MM:ss:sss”)部分。

非常感谢任何帮助或建议。

谢谢

共有3个答案

仲孙昊焱
2023-03-14

第一个建议是转移到java8 java.time API,而不是学习不完善的java.date API

然后执行以下操作:

Instant i = Instant.now();
System.out.println(i.toEpochMilli());

在您的情况下,您可以执行以下操作:

LocalDateTime myldt = LocalDateTime.parse("2017-06-14 14:29:04",
        DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"));
System.out.println(myldt.toInstant(ZoneOffset.UTC).toEpochMilli());

请注意,只要您使用 API 玩得更多,您就会找到更多实现相同目标的方法,最后您将结束调用 toEpochMilli

澹台新知
2023-03-14

首先,检查 SimpleDateFormat 的文档。对应于毫秒的模式是大写的 S,而小写的 s 对应于秒。问题是 SimpleDateFormat 通常不会抱怨并尝试将 423 解析为秒,将此数量添加到您的结束日期(给出不正确的结果)。

总之,< code>SimpleDateFormat只是将< code >字符串解析为< code>java.util.Date或将< code >日期格式化为< code >字符串。如果需要纪元毫秒值,必须从< code>Date对象中获取:

// input string
String s = "2017.07.19 11:42:30:423";
// use correct format ('S' for milliseconds)
SimpleDateFormat formatter = new SimpleDateFormat("yyyy.MM.dd HH:mm:ss:SSS");
// parse to a date
Date date = formatter.parse(s);
// get epoch millis
long millis = date.getTime();
System.out.println(millis); // 1500475350423

问题是< code>SimpleDateFormat使用系统的默认时区,所以上面的最终值(< code>1500475350423)将等同于我的系统时区中指定的日期和时间(可能与您的时区不同——为了记录起见,我的系统的默认时区是< code>America/Sao_Paulo)。如果要指定这个日期所在的时区,需要在格式化程序中设置(在调用< code>parse之前):

// set a timezone to the formatter (using UTC as example)
formatter.setTimeZone(TimeZone.getTimeZone("UTC"));

这样,millis 的结果将1500464550423(相当于 UTC 中的特定日期和时间)。

要做相反的事情(从Millis值创建日期),您必须创建一个Date对象,然后将其传递给格式化程序(还要注意为格式化程序设置时区):

// create date from millis
Date date = new Date(1500464550423L);
// use correct format ('S' for milliseconds)
SimpleDateFormat formatter = new SimpleDateFormat("yyyy.MM.dd HH:mm:ss:SSS");
formatter.setTimeZone(TimeZone.getTimeZone("UTC"));
// format date
String formatted = formatter.format(date);

旧类(DateCalendarSimpleDateFormat)有很多问题和设计问题,它们正在被新的API所取代。

如果您使用的是Java 8,请考虑使用新的Java。时间API。与旧的API相比,它更容易、更少的错误和更少的错误。

如果你用的是Java

下面的代码适用于两者。唯一的区别是包名称(在Java8中是java.time,在Threeten Backport(或Android的ThreetenABP)中是org.threeten.bp),但类和方法名称是相同的。

由于输入的< code>String没有时区信息(只有日期和时间),首先我将其解析为< code>LocalDateTime(一个表示没有时区的日期和时间的类)。然后,我将这个日期/时间转换为特定的时区,并从中获取毫秒值:

// input string
String s = "2017.07.19 11:42:30:423";
// use correct format ('S' for milliseconds)
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy.MM.dd HH:mm:ss:SSS");
// as the input string has no timezone information, parse it to a LocalDateTime
LocalDateTime dt = LocalDateTime.parse(s, formatter);

// convert the LocalDateTime to a timezone
ZonedDateTime zdt = dt.atZone(ZoneId.of("Europe/London"));
// get the millis value
long millis = zdt.toInstant().toEpochMilli(); // 1500460950423

值现在是1500460950423,相当于伦敦时区中的指定日期和时间。

请注意,API使用IANA时区名称(始终采用地区/城市格式,如America/Sao_Pauloor )。避免使用3个字母的缩写(如 CSTPST),因为它们不明确且不标准。

您可以通过调用 ZoneId.getAvailableZoneIds() 来获取可用时区的列表(并选择最适合您系统的时区)。

您还可以使用<code>ZoneOffset。如果要使用UTC,UTC常量。

要做相反的事情,你可以获取 millis 值来创建即时,将其转换为时区并将其传递给格式化程序:

// create Instant from millis value 
Instant instant = Instant.ofEpochMilli(1500460950423L);
// use correct format ('S' for milliseconds)
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy.MM.dd HH:mm:ss:SSS");
// convert to timezone
ZonedDateTime z = instant.atZone(ZoneId.of("Europe/London"));
// format
String formatted = z.format(formatter);
令狐嘉禧
2023-03-14

您在格式模式字符串中使用大小写时有一个简单的错误(这些是区分大小写的)。更糟糕的是,您使用的是旧的且麻烦的SimpleDateForata类。它的许多问题之一是它没有告诉您问题是什么。

因此,我建议您使用现代Java日期和时间API(我故意逐字使用您的格式模式字符串):

    String receivedTimetamp = "2017.07.19 11:42:30:423";
    DateTimeFormatter parseFormatter
            = DateTimeFormatter.ofPattern("yyyy.MM.dd HH:mm:ss:sss");
    LocalDateTime dateTime = LocalDateTime.parse(receivedTimetamp, parseFormatter);
    System.out.println(dateTime);

此代码抛出IllegalArgumentException:模式字母太多:s。我希望这能唤起你的意识,你用两个s表示秒,用三个s表示零碎秒。如果仍然不清楚,文档将告诉您小写的s对于秒是正确的,而您需要大写的s来表示分数。让我们修复:

    DateTimeFormatter parseFormatter
            = DateTimeFormatter.ofPattern("yyyy.MM.dd HH:mm:ss:SSS");

现在,代码打印2017-07-19T11:42:30.423,因此我们成功地解析了字符串。

为了转换为毫秒,我们仍然缺少一条关键信息:应该在哪个时区解释时间戳?我认为两个明显的猜测是UTC和您的本地时区(我不知道)。尝试 UTC:

    System.out.println(dateTime.atOffset(ZoneOffset.UTC).toInstant().toEpochMilli());

这将生成1500464550423,这是您要求的号码。我想我们完了。

如果您想要JVM的时区设置,请使用. atZone(ZoneId.system默认值())而不是. atoffset(ZoneOffset.UTC),但请注意该设置可能会被在同一JVM中运行的其他软件更改,因此这很脆弱。

 类似资料:
  • 问题内容: 我有一个来自sqllite数据库的格式化日期,要在图形视图中使用它,我需要将其格式化为长整数。 格式为: 2012-07-11 10:55:21 如何将其转换为毫秒? 问题答案: 您可以使用以下代码将字符串转换为Date对象: 然后使用内置方法将其转换为毫秒

  • 问题内容: 这是我的代码: 是否可以在日期格式中添加毫秒和纳秒? 问题答案: 您可以通过在末尾添加来添加毫秒数,例如格式为。 毫微秒内没有参考。通常用于性能调试,而不用于显示目的。

  • 问题内容: 我正在尝试将一个长值(从1970年1月1日经过的毫秒数,即Epoch)转换为格式时间。 我用作时间戳记的长值,是从log4j的日志记录事件字段获得的。 到目前为止,我已经尝试了以下操作,但失败了: 但我得到了不正确的值: 我该怎么办? 问题答案: 尝试这个: 有关该类接受的其他格式字符串的说明,请参见SimpleDateFormat。 请参见使用1200 ms输入的可运行示例。

  • 返回给定毫秒数的可读格式。 用适当的值来划分ms,以获得 day,hour,minute,second 和 millisecond 的适当值。 通过 Array.filter() 使用 Object.entries() 只保留非零值。 使用 Array.map() 为每个值创建字符串,并且适当复数化。 使用 String.join(', ') 将这些值组合成一个字符串。 const formatD

  • 问题内容: 我有一个$ i变量,它在shell脚本中是秒,并且我试图将其转换为24小时HH:MM:SS。这在壳中可能吗? 问题答案: 这是一种有趣的hacky方式,可以完全满足您的需求=) 说明: 该实用程序允许您从字符串开始以秒为单位指定从1970-01-01 00:00:00 UTC开始的时间,并以您指定的任何格式输出时间。 该选项是显示UTC时间,因此不考虑时区偏移量(因为从1970年开始的

  • 问题内容: 我正在创建一个HTML表,将在Excel中作为电子表格打开。我可以使用哪种HTML标记或CSS样式“讲述” Excel以将单元格的内容显示为文本? 问题答案: 您可以将格式应用于数字,文本,日期等的单元格。 请参阅我以前关于此的答案:HTML toExcel:如何告诉Excel将列视为数字? (已调整的代码段) 如果将CSS类添加到页面: 并在您的TD上拍那些课,行得通吗?