Java8 时间类

1、介绍

在Java8之前,日期时间API一直被开发者诟病,包括:java.util.Date是可变类型,SimpleDateFormat非线程安全等问题。故此,Java8引入了一套全新的日期时间处理API,新的API基于ISO标准日历系统。

2、名词

时间戳(时刻):时间戳是指格林尼治时间1970年01月01日00时00分00秒到现在的总秒数(毫秒数),可以理解成绝对时间,它与时区无关,不同时区对同一时间戳的解读不一样
时区:同一时刻(时间戳),世界上各地区的时间可能是不一样的,具体时间与时区相关,按经度一共分为24个时区,英国格林尼治是0时区,中国北京是东8区

二、Java8时间

2.1 Java8时间
Java1.0版本时,对时间的支持仅有java.util.Date类,它表示从1970-01-01 00:00:00开始精确到毫秒的时间点。到Java1.1时,表示日期的java.util.Calendar类被添加进来,但Calendar类也存在很多问题,比如:Date、Calendar类都是可变的,但像时间、日期这样的类应该是不变的;Date中月份是从0开始的;格式化只对Date生效,对Calendar不生效。2001年左右,Joda-Time项目开始致力于提供一个高质量的时间和日期的类库,因为其易用性很快得到了广泛使用。Java8借鉴了大量Joda-Time特性,推出了新的时间工具包

Java8时间相关类在java.time包路径下,表示时间的主要类如下:
Instant 时间戳(时刻)
LocalDate 与时区无关的日期
LocalTime 与时区无关的时间
LocalDateTime 与时区无关的日期和时间
ZonedDateTime 与时区相关的日期和时间
ZoneId 时区
ZoneOffset 相对于格林尼治时间的时间偏差,比如:+08:00

时间输出格式类型:

输出类型 描述
2019-06-10T03:48:20.847Z
世界标准时间,T:日期和时间分隔,Z:世界标准时间
2019-06-10T11:51:48.872
不含时区信息的时间
2019-06-10T11:55:04.421+08:00[Asia/Shanghai]
包含时区信息的时间,+08:00表示相对于0时区加8小时,[Asia/Shanghai]:时区
3、Java8时间使用
构造Instant:

    public static void main(String ... args) {
        // 获取当前时间戳
        Instant instant = Instant.now();
        System.out.println(instant);
        // 指定系统时间戳
        Instant instant1 = Instant.ofEpochMilli(System.currentTimeMillis());
        System.out.println(instant1);
        // 解析指定时间戳
        Instant instant2 = Instant.parse("2019-06-10T03:42:39Z");
        System.out.println(instant2);
    }
--- 
2020-03-07T03:35:32.062Z
2020-03-07T03:35:32.063Z
2019-06-10T03:42:39Z

构造LocalDateTime:

     public static void main(String ... args) {
        // 获取当前时间
        LocalDateTime localDateTime = LocalDateTime.now();
        System.out.println(localDateTime);
		// 指定时间
        LocalDateTime localDateTime1 = LocalDateTime.of(2019, 06, 10, 10, 30,30);
        System.out.println(localDateTime1);
		// 解析时间
        LocalDateTime localDateTime2 = LocalDateTime.parse("2019-06-10 11:55:04", DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"));
        System.out.println(localDateTime2);
    }
---
2020-03-07T11:38:57.870
2019-06-10T10:30:30
2020-03-07T11:55:04

构造ZonedDateTime:

    public static void main(String ... args) {
		// 获取当前时区当前时间
        ZonedDateTime zonedDateTime = ZonedDateTime.now();
        System.out.println(zonedDateTime);
		// 指定时间及时区
        ZonedDateTime zonedDateTime1 = ZonedDateTime.of(2019, 06, 10, 10, 30,30, 00,  ZoneId.of("UTC"));
        System.out.println(zonedDateTime1);
		// 解析指定时间
        ZonedDateTime zonedDateTime2 = ZonedDateTime.parse("2019-06-10T12:03:19.367+08:00[Asia/Shanghai]", DateTimeFormatter.ISO_ZONED_DATE_TIME);
        System.out.println(zonedDateTime2);
    }
---
2019-06-10T12:08:44.405+08:00[Asia/Shanghai]
2019-06-10T10:30:30Z[UTC]
2019-06-10T12:03:19.367+08:00[Asia/Shanghai]

时间调整(TemporalAdjuster)

    public static void main(String ... args) {
        LocalDateTime localDateTime = LocalDateTime.now();
        // 本年本月最后一天
        System.out.println(localDateTime.with(TemporalAdjusters.lastDayOfMonth()));
        // 本年本月第一天
        System.out.println(localDateTime.with(TemporalAdjusters.firstDayOfMonth()));
        // 本年下一月第一天
        System.out.println(localDateTime.with(TemporalAdjusters.firstDayOfNextMonth()));
        // 下一年第一天
        System.out.println(localDateTime.with(TemporalAdjusters.firstDayOfNextYear()));
        // 本年最后一天
        System.out.println(localDateTime.with(TemporalAdjusters.lastDayOfYear()));
        // 下一个周五
        System.out.println(localDateTime.with(TemporalAdjusters.next(DayOfWeek.FRIDAY)));
        // 本月第一个周五
        System.out.println(localDateTime.with(TemporalAdjusters.firstInMonth(DayOfWeek.FRIDAY)));
        // 本月最后一个周五
        System.out.println(localDateTime.with(TemporalAdjusters.lastInMonth(DayOfWeek.FRIDAY)));
        // 下一个周五,如果当前是周五则返回当前时间
        System.out.println(localDateTime.with(TemporalAdjusters.nextOrSame(DayOfWeek.FRIDAY)));
        // 前一个周五
        System.out.println(localDateTime.with(TemporalAdjusters.previous(DayOfWeek.FRIDAY)));
        // 前一个周五,如果当前是周五则返回当前时间
        System.out.println(localDateTime.with(TemporalAdjusters.previousOrSame(DayOfWeek.FRIDAY)));
        // 当前时间+100天,plusYeas/plusMonths/plusWeeks/plusHours/plusMinutes/plusSeconds形式相同,同于System.out.println(localDateTime.plus(100, ChronoUnit.DAYS));
        System.out.println(localDateTime.plusDays(100));
        // 当前时间-100天,minusYeas/minusMonths/minusWeeks/minusHours/minusMinutes/minusSeconds形式相同,同于System.out.println(localDateTime.minus(100, ChronoUnit.DAYS));
        System.out.println(localDateTime.minusDays(100));
    }
---
2019-07-31T20:19:49.250
2019-07-01T20:19:49.250
2019-08-01T20:19:49.250
2020-01-01T20:19:49.250
2019-12-31T20:19:49.250
2019-07-19T20:19:49.250
2019-07-05T20:19:49.250
2019-07-26T20:19:49.250
2019-07-19T20:19:49.250
2019-07-12T20:19:49.250
2019-07-12T20:19:49.250
2019-10-22T20:19:49.250
2019-04-05T20:19:49.250

参考文章:Java中的时间与时区
Java8日期/时间使用
java8日期屌炸天特性以及实战

发布了80 篇原创文章 · 获赞 140 · 访问量 64万+

猜你喜欢

转载自blog.csdn.net/linjpg/article/details/104711870