3.1 KiB
3.1 KiB
JDK与时间相关的包和API:
包
| 包 | 引入 | 描述 |
|---|---|---|
| java.time | 1.8+ | 推荐使用 |
| java.util | 旧版 | 不推荐 |
| java.text | 旧版 | 日期字符串格式化相关,不推荐使用 |
| java.sql | 1.1 | 数据库相关,业务不推荐使用 |
| java.time.chrono | 1.8 | 可选,能不用就不用。支持非 ISO 历法系统 |
java.time包中的类
| 类/接口 | 用途 |
|---|---|
LocalDate |
日期(年-月-日) |
LocalTime |
时间(时:分:秒.纳秒) |
LocalDateTime |
日期+时间 |
ZonedDateTime |
带时区的日期时间 |
Instant |
时间戳(从1970-01-01的秒/毫秒) |
Duration |
时间间隔(基于秒和纳秒) |
Period |
日期间隔(基于年月日) |
DateTimeFormatter |
日期时间格式化 |
| LocalDate,LocalTime,LocalDateTime都是指表示一个时间数字,没有时区概念。比如LocalTime表示8:20,并不能表示出具体的时间,需要结合时区才能知道是哪里的8:20。 |
java.time.format DateTimeFormatter 及其相关类 用于格式化与解析日期时间 java.time.temporal 时间访问和调整的底层接口 包含 Temporal, TemporalField, TemporalUnit 等
java.time.zone 时区相关类 ZoneId, ZoneOffset, ZoneRules 等
java.util包中的类
| 类 | 说明 |
|---|---|
Date |
传统日期类(已不推荐),不带时区 |
Calendar |
日历计算(已不推荐),默认系统时区 |
TimeZone |
时区信息 |
java.text包中的类
SimpleDateFormat - 旧版日期格式化(线程不安全)
java.sql
这些也都没有时区概念,只表示时间值
| 类 | 用途 |
|---|---|
Date |
SQL 日期 |
Time |
SQL 时间 |
Timestamp |
SQL 时间戳 |
最佳实践
关于时区:
- 系统内部应该只用java.time下的LocalDate,LocalTime,LocalDateTime这些不带时区的概念。
- 只有与外部交互时,才应该转成带时区的概念。 比如把前端请求的日期转成LocalDateTime,返回给前端的时间应该转成前端对应时区的时间。或者请求外部依赖时,需要传递时间,应该确定好时区的概念。
- 定时任务的时间设置应该带上时区,否则将会按照系统所在时区执行,切换服务器时,时区会变,定时任务的执行时间也会变。
作为中国开发者,应该都用东八区时间。
@Scheduled(cron = "2 15 0 * * ?", zone = "Asia/Shanghai") - 服务器的时区都设置成东八区时间
查看时区:timedatectl
列出可支持的时区:timedatectl list-timezones | grep Shanghai
设置时区:sudo timedatectl set-timezone Asia/Shanghai
关于存储时间的格式:
- 系统中只允许使用LocalDateTime,或者Long时间戳存储时间。优先用LocalDateTime,既拥有时间戳的所有信息,也有丰富的API操作时间。