-
- java8 datetime api有什么
- LocalDate
- LocalDate 与 Date 转换
- LocalTime
- LocalDateTime
- LocalDateTime 与 Date
- Instant
- ZoneId
- 日期计算
Java的日期时间API,一直有一些令人头疼的问题。
有了 java.util.Date 又搞出个java.sql.Date,改个名字不行?
好好的new Date(year,month,day) 早早的就被标记为 @Deprecated,那时候还是jdk1.1,如今都java9了,还没删除。
好吧,又给了一个Calendar,每次一个操作,都感觉,IDE一行设置80个字符,是真不够。
我想搞个纯日期,那叫一个麻烦,相信很多人都这么写:
Calendar cal=Calendar.getInstance();
cal.set(Calendar.HOUR,0);
cal.set(Calendar.MINUTE,0);
cal.set(Calendar.SECOND,0);
Date date=cal.getTime();
心塞~
貌似看起来Calendar比Date好一点,但他继承了Date一个很恶心的特性,月份问题。
System.out.println(cal.getTime());//Fri Nov 17 12:00:00 CST 2017
System.out.println(cal.get(Calendar.MONTH));//10
java8终于有了个改观,那就是引入了joda-time的API,虽然仍然没有joda好用。
java8 datetime api有什么?
日期时间API将日期和时间分开为LocalDate和LocalTime;
既有日期又有时间,则使用 LocalDateTime;
改善了jdk的TimeZone,使用更优雅的ZoneId;
增加了 Instant 的概念,可以理解为时间线上的一个瞬间;
LocalDate
//获取当前日期
LocalDate date1=LocalDate.now();
System.out.println(date1);
//获取指定日期
LocalDate date2=LocalDate.of(2017, 12, 24);
System.out.println(date2);
//获取当月第一天日期
LocalDate minus = date1.minus(date1.getDayOfMonth()-1,ChronoUnit.DAYS);
System.out.println(minus);
LocalDate 与 Date 转换
//LocalDate -> Date
LocalDate localDate1=LocalDate.now();
ZoneId zoneId=ZoneId.systemDefault();
Instant instant=localDate1.atStartOfDay(zoneId).toInstant();
Date from = Date.from(instant);
System.out.println(from);
//Date 转 LocalDate
Date date2=new Date();
Instant instant = date2.toInstant();
ZoneId zoneId=ZoneId.systemDefault();
LocalDate localDate2 = instant.atZone(zoneId).toLocalDate();
System.out.println(localDate);
LocalTime
实际单纯使用时间的场景,并没有单纯使用日期的时间多。而且,LocalDate的思路捋清楚,LocalTime的使用大同小异,以后再补充吧。
LocalDateTime
结合了LocalDate 和 LocalTime,也就是传统意义上类似Date的时间。
LocalDate localDate = dt.toLocalDate();
LocalTime localTime = dt.toLocalTime();
LocalDateTime 与 Date
Date 转 LocalDateTime
Date date = new Date();
Instant instant = date.toInstant();
ZoneId zone = ZoneId.systemDefault();
LocalDateTime localDateTime = LocalDateTime.ofInstant(instant, zone);
# LocalDateTime 转 Date
LocalDateTime localDateTime = LocalDateTime.now();
ZoneId zone = ZoneId.systemDefault();
Instant instant = localDateTime.atZone(zone).toInstant();
Date date = Date.from(instant);
Instant
从前面的格式转换可以看出。
Date -> Instant -(ZoneId)-> LocalDate
用文字描述,就是 Date 可以转换为 Instant;Instant 可以借助ZoneId 转换为LocalDate。反之亦然。
ZoneId
ZoneId zoneId=ZoneId.systemDefault();
System.out.println(zoneId);
TimeZone tz=TimeZone.getDefault();
System.out.println(tz);
输出:
Asia/Shanghai
sun.util.calendar.ZoneInfo[id="Asia/Shanghai",offset=28800000,dstSavings=0,useDaylight=false,transitions=19,lastRule=null]
ZoneId忽略了哪些用处不大的信息,更清晰。如果必要的时候,可以在属性 zoneId.getRules()
中获取。
日期计算
在日期计算上,引入的joda-time特性,实在太方便了。
比如,如果要得到本月的第一天的日期,那么以前我们需要这么做。
Calendar cal=Calendar.getInstance();
cal.set(Calendar.HOUR,0);
cal.set(Calendar.MINUTE,0);
cal.set(Calendar.SECOND,0);
cal.set(Calendar.DAY_OF_MONTH,1);
System.out.println(cal.getTime());
现在呢?
LocalDate date=LocalDate.now().withDayOfMonth(1);
System.out.println(date);
如果我们希望计算当前时间的前一天的时刻,以前需要这么做:
Calendar cal=Calendar.getInstance();
cal.add(Calendar.DAY_OF_MONTH, -1);
现在呢?
LocalDateTime date=LocalDateTime.now().minusDays(1);
既简单,语义也更佳。支持链式语法,编码方便。
我的博客即将入驻“”,诚邀技术同仁一同入驻。