在Java中获得"unixtime"

Gar*_*son 250 java unix-timestamp

Date.getTime()返回自1970年1月1日以来的毫秒数.Unixtime是自1970年1月1日以来的秒数.我通常不用java编写代码,但我正在修复一些错误.我有:

Date now = new Date();      
Long longTime = new Long(now.getTime()/1000);
return longTime.intValue();
Run Code Online (Sandbox Code Playgroud)

有没有更好的方法在java中获得unixtime?

UPDATE

根据John M的建议,我最终得到:

Date now = new Date();      
Long longTime = new Long(now.getTime()/1000);
return longTime.intValue();
Run Code Online (Sandbox Code Playgroud)

Joh*_*n M 463

避免使用System.currentTimeMillis()创建Date对象.除以1000可以获得Unix时代.

正如评论中所提到的,对于unixTime变量的类型,通常需要一个原始的long(小写l长)而不是boxed对象long(capital-L Long).

long unixTime = System.currentTimeMillis() / 1000L;
Run Code Online (Sandbox Code Playgroud)

  • Java 32位int匹配32位平台(以及2038年的问题).64位平台使用更大的time_t数据类型.Java使用long作为System.currentTimeMillis()的返回来避开该子弹.如果转换为int,则会重新引入2038年的问题.请参见http://en.wikipedia.org/wiki/Year_2038_problem#Solutions (8认同)
  • 资本化讨论(上文已阐明)是关于数据类型的.原始"long"vs"java.lang.Long"类实例.你在谈论长字面上的后缀字母,我同意可以是大写或小写.虽然小写"l"看起来很像数字"1",但使用大写"L"更易读. (4认同)
  • 还要考虑使用原始long而不是自动装箱到Long,除非你想将数字作为一个Object处理(比如将它放入一个Collection),再次避免不必要的对象创建 (3认同)

mic*_*cha 263

Java 8添加了一个用于处理日期和时间的新API.使用Java 8,您可以使用

import java.time.Instant
...
long unixTimestamp = Instant.now().getEpochSecond();
Run Code Online (Sandbox Code Playgroud)

Instant.now()返回表示当前系统时间的Instant.随着getEpochSecond()你获得了纪元秒(unix时间)Instant.

  • 这应该是新接受的答案. (34认同)
  • 请查看此站点以获取详细说明...喜欢它.. [currentTimeMillis](https://currentmillis.com/tutorials/system-currentTimeMillis.html) (4认同)
  • `Instant.now().getEpochSecond()`,`new Date().getTime()`和`System.currentTimeMillis()`之间有什么区别? (3认同)
  • 如果你在Scala中,请输入java.time.Instant` (3认同)
  • 一个区别是前者以秒为单位,而后两者以毫秒为单位。可能有也可能没有其他人。 (2认同)
  • 请注意,您不能将此方法用于较旧的 android API 级别。 (2认同)

Ole*_*.V. 5

已经有两个很好的答案了。在新的副本之际,我将在两个方向上更深入地研究:

\n
    \n
  1. 在java 7上做什么?
  2. \n
  3. 如何编写可测试的版本?
  4. \n
\n

对于Java 7

\n

如果您仍在使用 Java 7,您仍然可以选择要使用的其他答案。Micha 提到 java.time 是在 Java 8 中引入的。但是 java.time 也在ThreeTen Backport中向后移植到了 Java 6 和 7 。对于获取 Unix 时间戳来说,获取向后移植似乎有些过分,但如果您在程序中执行更多日期和时间工作,我仍然认为您应该考虑它。底部有\xe2\x80\x99s 链接。

\n

另外,在您自己的代码中除以 1000 似乎是一件很小的事情。尽管如此,我仍然养成了将尽可能多的日期和时间工作留给标准库(最好是 java.time)的习惯。在许多其他情况下,转换看起来很容易,但很容易出错。所以我不想在我的代码中执行它们。所以我的纯 Java 7 解决方案(没有外部库/向后移植)可能如下所示:

\n
    long unixTime = TimeUnit.MILLISECONDS.toSeconds(System.currentTimeMillis());\n    System.out.println(unixTime);\n
Run Code Online (Sandbox Code Playgroud)\n
\n

1636883947

\n
\n

现在我也告诉读者为什么我要除以 1000。虽然代码有点长,但也更不言自明。

\n

更具可测试性

\n

java.time 还为 Java 7 和 8 及更高版本提供可测试的解决方案。我们可以注入 a Clock,当前时间的来源。

\n
    Clock clock = Clock.systemUTC();\n    long unixTime = Instant.now(clock).getEpochSecond();\n    System.out.println(unixTime);\n
Run Code Online (Sandbox Code Playgroud)\n

刚才的输出:

\n
\n

1636882578

\n
\n

(我使用 ThreeTen Backport 1.3.6 在 Java 1.7.0_67 上运行了这个。)

\n

在需要控制用于获得可重现结果的时间的测试中,例如获取具有固定时间的时钟:

\n
    Clock clock = Clock.fixed(Instant.ofEpochSecond(1_635_936_963), ZoneOffset.UTC);\n
Run Code Online (Sandbox Code Playgroud)\n

现在代码的输出是我们指定的时间:

\n
\n

1635936963

\n
\n

如果您想要的只是Clocks Instant,因为 Java 17 不再使用Clock. 使用InstantSource

\n
    InstantSource instantSource \n            = InstantSource.fixed(Instant.ofEpochSecond(1_654_321_098));\n    long unixTime = instantSource.instant().getEpochSecond();\n
Run Code Online (Sandbox Code Playgroud)\n
\n

1654321098

\n
\n

链接

\n\n