在Java8之前通常会使用Date结合SimpleDateFormat、Calender来处理时间和日期的相关需求。
1、可读性差、易用性差、使用起来冗余繁琐
2、java.util.Date 是非线程安全的
3、java.util.Date 存在千年虫问题、并且不支持国际化和时区、故大部分方法被声明为过时、不建议再使用
4、java.util和java.sql两包中都有Date类,设计上并不合理
Java8新增的日期类主要有三个:
LocalDate:表示日期(年月日)
LocalTime :表示时间(时分秒)
LocalDateTime:表示日期 + 时间(年月日时分秒),是java8最常用的日期类
这些类使用了final来修饰,使得这些类是不可变的,一旦实例化,值就固定了,有点类似于String类。
因此它们都是线程安全的。
在本文中会用到时区,所以给大家介绍几个常用的时区。
函数声明 | 描述 |
---|---|
ZoneId.of(“Asia/Shanghai”) | 上海 |
ZoneId.of(“Asia/Chongqing”) | 重庆 |
ZoneId.of(“Asia/Chungking”) | 重庆 |
ZoneId.of(“Asia/Hong_Kong”) | 香港 |
ZoneId.of(“Hongkong”) | 香港 |
可以使用下面代码查看所有时区。
Set<String> availableZoneIds = ZoneId.getAvailableZoneIds();
System.out.println(availableZoneIds.size());
availableZoneIds.forEach(System.out::println);
函数声明 | 描述 |
---|---|
static LocalDateTime now() | 获取默认时区的当前日期时间 |
LocalDate of(int year, int month, int dayOfMonth) | 根据指定年月日创建LocalDate对象 |
static LocalDate now(ZoneId zone) | 获取指定时区的当前日期对象 |
static LocalDate now(Clock clock) | 从指定时钟获取当前日期对象 |
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd");
// 获取当前日期
LocalDate now = LocalDate.now();
// 指定时区
LocalDate now2 = LocalDate.now(ZoneId.of("Asia/Shanghai"));
LocalDate now3 = LocalDate.now(ZoneId.of("Canada/Yukon"));
// 指定时钟
LocalDate now4 = LocalDate.now(Clock.systemDefaultZone());
// 指定时间
LocalDate date1 = LocalDate.of(1999, 12, 5);
System.out.println("now : " + now.format(formatter));
System.out.println("now2 : " + now2.format(formatter));
System.out.println("now3 : " + now3.format(formatter));
System.out.println("now4 : " + now4.format(formatter));
System.out.println("date1 : " + date1.format(formatter));
函数声明 | 描述 |
---|---|
int getYear() | 获取年份 |
Month getMonth() | 获取月份,返回值为月份的枚举 |
int getMonthValue() | 获取月份,返回值为int类型月份 |
DayOfWeek getDayOfWeek() | 获取日期是星期几 |
int getDayOfMonth() | 获取日期在该月是第几天 |
int getDayOfYear() | 获取日期在该年是第几天 |
int lengthOfMonth() | 本月份总天数 |
int lengthOfYear() | 本年度总天数 |
long toEpochDay() | 与时间纪元(1970年1月1日)相差的天数 |
LocalDate now = LocalDate.now();
System.out.println("getYear : " + now.getYear());
System.out.println("getMonth : " + now.getMonth());
System.out.println("getMonthValue : " + now.getMonthValue());
System.out.println("getDayOfMonth : " + now.getDayOfMonth());
System.out.println("getDayOfWeek : " + now.getDayOfWeek());
System.out.println("getDayOfYear : " + now.getDayOfYear());
System.out.println("lengthOfMonth : " + now.lengthOfMonth());
System.out.println("lengthOfYear : " + now.lengthOfYear());
System.out.println("toEpochDay : " + now.toEpochDay());
函数声明 | 描述 |
---|---|
LocalDate plusYears(long years) | 增加年 |
LocalDate plusMonths(long months) | 增加月份 |
LocalDate plusWeeks(long weeks) | 增加周 |
LocalDate plusDays(long days) | 增加日 |
LocalDate minusYears(long years) | 减少年 |
LocalDate minusMonths(long months) | 减少月份 |
LocalDate minusWeeks(long weeks) | 减少周 |
LocalDate minusDays(long days) | 减少日 |
LocalDate withDayOfMonth(int dayOfMonth) | 替换月份中的第几天(1-31) |
LocalDate withDayOfYear(int dayOfYear) | 替换年份中的第几天(1-366) |
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd");
// 获取当前日期
LocalDate now = LocalDate.now();
System.out.println("now : " + now.format(formatter));
System.out.println("plusDays : " + now.plusDays(1));
System.out.println("minusDays : " + now.minusDays(-1));
System.out.println("-------------------------------------");
System.out.println("plusDays : " + now.plusDays(-2));
System.out.println("minusDays : " + now.minusDays(2));
System.out.println("withDayOfMonth : " + now.withDayOfMonth(2));
System.out.println("withDayOfYear : " + now.withDayOfYear(36));
plusXxx是增加时间,minusXxx是减少时间,但查看源码可以发现minusXxx还是用的plusXxx,所以这两类方法传参可为正数,也可为负数。正负号相同、数字相同时效果相反。
函数声明 | 描述 |
---|---|
boolean isEqual(ChronoLocalDate other) | 判断日期时间是否相等 |
boolean isAfter(ChronoLocalDate other) | 检查是否在指定日期时间之前 |
boolean isBefore(ChronoLocalDate other) | 检查是否在指定日期时间之后 |
boolean isLeapYear() | 是否是闰年 |