正如我们在上一个问题中所发现的,java中的长时间戳意味着Unix时间戳:
long ts = 1362156863140L
但是Java中有朴素的时间戳吗?还是将构造函数中的长时间戳视为不知道时区的类?
您使用的术语很有趣。 根据大多数定义,"时间戳"是唯一的时间点,因此必须与 UTC 相关 - 要么完全基于 UTC,要么与 UTC 有固定的偏移量。 因此,"幼稚时间戳"在某种程度上是矛盾的。
但是,确实有一个类表示没有时区的日期和时间,这是LocalDateTime
. 它是作为 Java 8 中的 JSR-310 引入的java.time
API 的一部分。
您可以使用LocalDateTime.ofEpochSecond
从数字时间戳创建一个时间戳。 如果您的时间戳是基于毫秒的,那么您可以执行一些除法和模法以将其拆分为单独的秒和纳秒参数。 您还需要向它传递 UTC 偏移量,以便它知道您希望如何解释传入的值。
tl;博士
您使用的术语相互矛盾。根据定义,时间戳需要时区或 UTC 偏移量。
了解以下各项之间的区别:
- 时间轴上的一个点(引用时区或与 UTC 的偏移量)
- 与时间线无关的日期/时间(缺乏区域/偏移量的概念)
每个都有一个目的,但只有第一个代表一个特定的时刻。"时间戳"一词的意思是第一个而不是第二个。
Instant
有吗。。。爪哇中的时间戳?
是的,Instant
是一个时间戳。Instant
类以 UTC 表示时间轴上的时刻,分辨率为纳秒(最多九 (9) 位小数)。
Instant instant = Instant.now() ; // Capture the current moment in UTC.
如果自纪元参考日期 1970-01-01T00:00:00Z 以来的计数为毫秒,则解析为Instant
。末尾的Z
表示UTC,发音为"祖鲁"。
long millisSinceEpoch = 1_362_156_863_140L ;
Instant instant = Instant.ofEpochMilli( millisSinceEpoch );
2013-03-01T16:54:23.140Z
需要时区
将构造函数中的长时间戳视为不知道时区的类
你在术语上使用矛盾。时间戳,如果您指的是时间轴上的一个点,即历史中的特定时刻,则必然涉及时区或 UTC 偏移量。根据定义,时间戳不能不知道时区。
通常在日期时间处理中,我们使用 UTC 作为跟踪时间的基线。 格林威治皇家天文台通过历史怪癖的那句话通常被用作我们定义新一天的任意选择。
至于1970-01-01T00:00:00Z的纪元参考日期,这只是信息技术行业使用的几十个或更多的纪元参考之一。
如果没有时区或 UTC 偏移量,我们就缺乏一个上下文,可以在其中赋予日期和时间以意义。例如,"下周五中午"在印度可能意味着中午 12 点,在法国可能意味着中午 12 点,每个时间相隔几个小时。另一个例子是,突尼斯午夜过后几分钟是新的一天,而在魁北克,它仍然是"昨天"。
如果我们指定一个时区,例如"太平洋/奥克兰的下周五中午",那么我们就是一个特定的时刻,一个时间轴上的一个点。
ZoneId z = ZoneId.of( "Pacific/Auckland" ) ;
LocalDate todayAuckland = LocalDate.now( z ) ; // Need time zone to determine today’s date.
LocalDate sameOrNextFriday = todayAuckland.with( TemporalAdjusters.next( DayOfWeek.FRIDAY ) ;
LocalTime timeOfDay = LocalTime.of( 12 , 0 ) ;
ZonedDateTime noonNextFridayAuckland = ZonedDateTime.of( sameOrNextFriday , timeOfDay , z ) ; // Determines a specific moment on the timeline.
Instant noonNextFridayAucklandViewedAsUtc = noonNextFridayAuckland.toInstant() ; // Same moment, same point on the timeline, but viewed with wall-clock time of UTC.
未分区
Java 中有朴素的时间戳吗?
如果您所说的"幼稚"是指故意缺乏时区概念或 UTC 偏移量的日期时间,是的:LocalDateTime
。但不要将这样的值称为"时间戳"。
Java 中的所有三个Local…
类都故意缺少区域/偏移量。
LocalDateTime
LocalDate
LocalTime
我有一种沉沦的感觉,你相信你可以通过忽略时区和偏移量的问题来让你的编程生活更轻松。你不能。您将玩一个冒险的"现在付款,或稍后付款"的游戏。
虽然您确实可以将Local…
类型用于仅具有家乡用户的应用程序,但一旦您的软件必须处理该狭隘范围之外的任何情况,您就会面临灾难。如果您需要与另一个城镇的某人进行约会,或将日志条目与远程服务器进行比较,或与其他软件系统进行通信,那么您将面临一团糟。
那么为什么java.time包含LocalDateTime
或LocalDate
或LocalTime
?何时应使用这些类?三种情况:
- 区域或偏移量未知。
这很糟糕。这是错误的数据。类似于在不知道货币的情况下拥有价格/成本。 - 意图是"无处不在">,就像每个时区一样.
示例,公司政策规定"我们所有的工厂将在 12:30 休息午餐"意味着德里的工厂将在杜塞尔多夫工厂之前几个小时休息,而杜塞尔多夫工厂比底特律工厂早几个小时休息。 - 未来的特定时刻是有意的,但我们害怕政客们重新定义时区。
政府以惊人的频率改变其时区的规则,而且令人惊讶的是几乎没有警告(甚至根本没有警告)。因此,如果您想在某个日期的下午 3 点预约,而您实际上的意思是下午 3 点,而不管政府在此期间可能做出的任何疯狂决定,那么请存储一个LocalDateTime
。要打印报告或显示日历,请动态应用时区(ZoneId
)以生成特定时刻(ZonedDateTime
或Instant
)。这必须即时完成,而不是存储值。
关于java.time
java.time框架内置于 Java 8 及更高版本中。这些类取代了麻烦的旧旧日期时间类,如java.util.Date
、Calendar
和SimpleDateFormat
。
Joda-Time项目现在处于维护模式,建议迁移到 java.time 类。
要了解更多信息,请参阅Oracle 教程。并搜索堆栈溢出以获取许多示例和解释。规范为 JSR 310。
您可以直接与数据库交换java.time对象。使用符合 JDBC 4.2 或更高版本的 JDBC 驱动程序。不需要字符串,不需要java.sql.*
类。
从哪里获得java.time类?
Java SE 8、Java SE- 9、Java SE 10及更高版本
- 内置。
- 具有捆绑实现的标准 Java API 的一部分。
- Java 9添加了一些小功能和修复。
Java SE 6 和 Java SE 7 大部分 - java.time 功能在ThreeTen-Backport中向后移植到 Java 6 和 7。
Android- 更高版本的 java.time 类的 Android 捆绑实现。
- 对于早期的Android(<26),ThreeTenABP项目适应了ThreeTen-Backport(如上所述)。请参阅如何使用ThreeTenABP...。
ThreeTen-Extra项目通过额外的类扩展了java.time。这个项目是未来可能添加到java.time的试验场。你可以在这里找到一些有用的类,如Interval
、YearWeek
、YearQuarter
等。
从 1.8 开始,Java 有一个日期/时间 API,其中包含您可能需要的所有本机日期和时间函数。
请查看下面的URL以获取介绍和许多示例: http://www.oracle.com/technetwork/articles/java/jf14-date-time-2125367.html