Java -- JodaTime第三方库操作时间
Posted MinggeQingchun
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Java -- JodaTime第三方库操作时间相关的知识,希望对你有一定的参考价值。
Java自带日期格式化工具DateFormat ,但是DateFormat 的所有实现,包括 SimpleDateFormat 都不是线程安全的,因此不应该在多线程序中使用,除非是在对外线程安全的环境中使用,如将 SimpleDateFormat 限制在 ThreadLocal 中。如果不这么做,在解析或者格式化日期的时候,可能会获取到一个不正确的结果。所以,通常我们使用第三方库Joda Time来进行时间相关的操作
一、导入JodaTime
1、在Maven中
<dependency>
<groupId>joda-time</groupId>
<artifactId>joda-time</artifactId>
<version>2.10.5</version>
</dependency>
2、在Gradle中
compile 'joda-time:joda-time:2.10.5'
二、JodaTime核心类
使用最多的五个日期时间类:
- Instant - 不可变的类,用来表示时间轴上一个瞬时的点(时间戳)
- DateTime - 不可变的类,用来替换JDK的Calendar类
- LocalDate - 不可变的类,表示一个本地的日期,而不包含时间部分(没有时区信息)
- LocalTime - 不可变的类,表示一个本地的时间,而不包含日期部分(没有时区信息)
- LocalDateTime - 不可变的类,表示一个本地的日期-时间(没有时区信息)
// joda创建时间对象时需要指定时区,如果不指定,默认会把时区设置为运行代码的机器所在的时区
DateTime dateTime0 = new DateTime(2022, 7, 3, 11, 0, 0).withZone(DateTimeZone.forID("Asia/Shanghai"));
System.out.println("dateTime0----" + dateTime0.toDate());
三、DateTime实例
当使用JodaTime的时候,首先你要获取一个DateTime实例,然后用它的其他方法串联起来实现强大的功能
/**
* 1、当使用JodaTime的时候,首先你要获取一个DateTime实例,然后用它的其他方法串联起来实现强大的功能。想要获取一个DateTime实例,你有很多种方式
* */
// 方式1:使用系统时间构造DateTime实例
DateTime dateTime = new DateTime();
// 方式2:使用具体的时间构造DateTime实例,该方法有许多重载版本
DateTime dateTime1 = new DateTime(
2022, // year
1, // month
1, // day
0, // hour (midnight is zero)
0, // minute
0, // second
0 // milliseconds
);
// 方式3:使用Calendar构造DateTime实例
DateTime dateTime2 = new DateTime(Calendar.getInstance());
System.out.println("dateTime2----" + dateTime2.toDate());
// 方式4:使用其他DateTime实例构造DateTime实例
DateTime dateTime3 = new DateTime(dateTime);
System.out.println("dateTime3----" + dateTime3.toDate());
// 方式5:使用字符串构造DateTime实例
DateTime dateTime4 = new DateTime("2022-01-26T13:30:00-06:00");
DateTime dateTime5 = new DateTime("2022-01-26");
System.out.println("dateTime4----" + dateTime4.toDate());
System.out.println("dateTime5----" + dateTime5.toDate());
四、DateTime方法
DateTime中有许多的方法,这里我们将常用的方法分成两类。一类是在方法中返回DateTime的那种,一类是在方法中返回Property类型的那种。显然,后面的那种继续串联操作的话,就需要调用Property的实例方法了
1、返回DateTime
/**
* 2、DateTime的方法
* DateTime中有许多的方法,这里我们将常用的方法分成两类。
* 一类是在方法中返回DateTime的那种,一类是在方法中返回Property类型的那种。
* 后面的那种继续串联操作的话,就需要调用Property的实例方法了
* */
// 指定的时间单位上面增加指定的值
DateTime dateTime00 = dateTime.plusDays(1);
System.out.println("dateTime00----" + dateTime00);
// 指定的时间单位上面减少指定的值
DateTime dateTime6 = dateTime.minusDays(1);
System.out.println("dateTime6----" + dateTime6);
// 除了增减日期还可以直接指定它的指定时间单位上面的值
DateTime dateTime7 = dateTime.withYear(2020);
System.out.println("dateTime7----" + dateTime7);
// 按照指定的格式输出日期
System.out.println(dateTime.toString("E MM/dd/yyyy HH:mm:ss.SSS"));
2、返回Property
以通过DateTime实例的millisOfDay() dayOfYear() minuteOfDay()等一些列方法可以获取到该DateTime的一个Property实例,然后可以通过调用Property的方法再获取一个DateTime实例。也就是说,实际上调用DateTime的方法获取Property实例是为了对指定的时间位置的信息进行修改。比如,对“日”进行修改,对“年”进行修改等等。修改了之后还是要获取一个DateTime实例,然后再继续进行后续的操作。
实际上每次调用DateTime的方法获取Property实例的时候,都会将当前的DateTime作为参数传入。然后当调用了指定的方法之后又会调用DateTime实例的withMillis()方法判断时间是否发生变化,如果发生了变化就创建一个新实例并返回
/**
* 3、使用Property
* 可以通过DateTime实例的millisOfDay() dayOfYear() minuteOfDay()等一些列方法可以获取到该DateTime的一个Property实例,然后可以通过调用Property的方法再获取一个DateTime实例。也就是说,实际上调用DateTime的方法获取Property实例是为了对指定的时间位置的信息进行修改。比如,对“日”进行修改,对“年”进行修改等等。修改了之后还是要获取一个DateTime实例,然后再继续进行后续的操作。
* 实际上每次调用DateTime的方法获取Property实例的时候,都会将当前的DateTime作为参数传入。然后当调用了指定的方法之后又会调用DateTime实例的withMillis()方法判断时间是否发生变化,如果发生了变化就创建一个新实例并返回
* */
// 这里先用dayOfMonth获取一个Property实例,然后调用它的withMaximumValue方法
// 它的含义是指定日期的其他日期不变,月份变成最大的之后返回一个DateTime,即如果传入的是2022年5月1日,将返回2022年5月31日,年,月,秒等位置不变,日变成该月最大的。
DateTime dateTime000 = dateTime.dayOfMonth().withMaximumValue();
DateTime dateTime111 = dateTime.dayOfMonth().withMinimumValue();
System.out.println("dateTime000----" + dateTime000);
System.out.println("dateTime111----" + dateTime111);
3、其他静态方法
/**
* 4、其他静态方法
* */
System.out.println("Days.daysBetween(dateTime1, dateTime).getDays()----" + Days.daysBetween(dateTime1, dateTime).getDays());
System.out.println("Months.monthsBetween(dateTime1, dateTime).getMonths()----" + Months.monthsBetween(dateTime1, dateTime).getMonths());
System.out.println("Years.yearsBetween(dateTime1, dateTime).getYears()----" + Years.yearsBetween(dateTime1, dateTime).getYears());
4、封装工具类
package com.mycompany.joda;
import org.joda.time.*;
import org.joda.time.format.DateTimeFormat;
import org.joda.time.format.DateTimeFormatter;
import java.util.Date;
public class JodaTimeUtil
private static final String PATTERN_STANDARD = "yyyy-MM-dd HH:mm:ss";
private static final String PATTERN_DATE = "yyyy-MM-dd";
private static final String PATTERN_TIME = "HH:mm:ss";
/**
* date类型 -> string类型
*
* @param date
* @return
*/
public static String date2Str(Date date)
if (date == null)
return "";
DateTime dateTime = new DateTime(date);
return dateTime.toString(PATTERN_STANDARD);
/**
* date类型 -> string类型
*
* @param date
* @param formatPattern
* @return
*/
public static String date2Str(Date date, String formatPattern)
if (date == null)
return "";
DateTime dateTime = new DateTime(date);
return dateTime.toString(formatPattern);
/**
* string类型 -> date类型
*
* @param timeStr
* @return
*/
public static Date str2Date(String timeStr)
DateTimeFormatter dateTimeFormatter = DateTimeFormat.forPattern(PATTERN_STANDARD);
DateTime dateTime = dateTimeFormatter.parseDateTime(timeStr);
return dateTime.toDate();
/**
* 获取指定时间
* @param year 年
* @param month 月
* @param day 日
* @param hour 时
* @param minute 分
* @param seconds 秒
* @return yyyy-MM-dd HH:mm:ss
*/
public static String getAssignedDateTime(Integer year, Integer month, Integer day, Integer hour, Integer minute, Integer seconds)
DateTime dt = new DateTime(year, month, day, hour, minute, seconds);
String date = dt.toString(PATTERN_STANDARD);
return date;
/**
* 获取指定日期
* @param year
* @param month
* @param day
* @return
*/
public static String getAssignedDate(Integer year, Integer month, Integer day)
LocalDate dt = new LocalDate(year, month, day);
String date = dt.toString(PATTERN_DATE);
return date;
/**
* 获取指定时间
* @param hour
* @param minutes
* @param seconds
* @return
*/
public static String getAssignedTime(Integer hour, Integer minutes, Integer seconds)
LocalTime dt = new LocalTime(hour, minutes, seconds);
String date = dt.toString(PATTERN_TIME);
return date;
/**
* 判断date日期是否过期(与当前时刻比较)
*
* @param date
* @return
*/
public static boolean isTimeExpired(Date date)
if (null == date)
return true;
String timeStr = date2Str(date);
return isBeforeNow(timeStr);
/**
* 判断date日期是否过期(与当前时刻比较)
*
* @param timeStr
* @return
*/
public static boolean isTimeExpired(String timeStr)
if (StringUtils.isBlank(timeStr))
return true;
return isBeforeNow(timeStr);
/**
* 判断timeStr是否在当前时刻之前
*
* @param timeStr
* @return
*/
private static boolean isBeforeNow(String timeStr)
DateTimeFormatter format = DateTimeFormat.forPattern(PATTERN_STANDARD);
DateTime dateTime = DateTime.parse(timeStr, format);
return dateTime.isBeforeNow();
/**
* 加天数
*
* @param date
* @param days
* @return
*/
private static Date plusDays(Date date, Integer days)
if (null == date)
return null;
days = null == days ? 0 : days;
DateTime dateTime = new DateTime(date);
dateTime = dateTime.plusDays(days);
return dateTime.toDate();
/**
* 减天数
*
* @param date
* @param days
* @return
*/
private static Date minusDays(Date date, Integer days)
if (null == date)
return null;
days = null == days ? 0 : days;
DateTime dateTime = new DateTime(date);
dateTime = dateTime.minusDays(days);
return dateTime.toDate();
/**
* 加分钟
*
* @param date
* @param minutes
* @return
*/
private static Date plusMinutes(Date date, Integer minutes)
if (null == date)
return null;
minutes = null == minutes ? 0 : minutes;
DateTime dateTime = new DateTime(date);
dateTime = dateTime.plusMinutes(minutes);
return dateTime.toDate();
/**
* 减分钟
*
* @param date
* @param minutes
* @return
*/
private static Date minusMinutes(Date date, Integer minutes)
if (null == date)
return null;
minutes = null == minutes ? 0 : minutes;
DateTime dateTime = new DateTime(date);
dateTime = dateTime.minusMinutes(minutes);
return dateTime.toDate();
/**
* 加月份
*
* @param date
* @param months
* @return
*/
private static Date plusMonths(Date date, Integer months)
if (null == date)
return null;
months = null == months ? 0 : months;
DateTime dateTime = new DateTime(date);
dateTime = dateTime.plusMonths(months);
return dateTime.toDate();
/**
* 减月份
*
* @param date
* @param months
* @return
*/
private static Date minusMonths(Date date, Integer months)
if (null == date)
return null;
months = null == months ? 0 : months;
DateTime dateTime = new DateTime(date);
dateTime = dateTime.minusMonths(months);
return dateTime.toDate();
/**
* 判断target是否在开始和结束时间之间
*
* @param target
* @param startTime
* @param endTime
* @return
*/
public static boolean isBetween(Date target, Date startTime, Date endTime)
if (null == target || null == startTime || null == endTime)
return false;
DateTime dateTime = new DateTime(target);
return dateTime.isAfter(startTime.getTime()) && dateTime.isBefore(endTime.getTime());
/**
* 获取当前系统时间
* @return yyyy-MM-dd HH:mm:ss
*/
public static String getCurrentDateTime()
DateTime dt = new DateTime();
String time = dt.toString(PATTERN_STANDARD);
return time;
/**
* 获取当前日期
* @return
*/
public static String getCurrentDate()
DateTime dt = new DateTime();
String date = dt.toString(PATTERN_DATE);
return date;
/**
* 获取系统当前时间按照指定格式返回
* @return
*/
public static String getCurrentTime()
DateTime dt = new DateTime();
String time = dt.toString(PATTERN_TIME);
return time;
/**
* 获取当前是一周星期几
* @return
*/
public static String getWeek()
DateTime dts = new DateTime();
String week = null;
switch (dts.getDayOfWeek())
case DateTimeConstants.SUNDAY:
week = "星期日";
break;
case DateTimeConstants.MONDAY:
week = "星期一";
break;
case DateTimeConstants.TUESDAY:
week = "星期二";
break;
case DateTimeConstants.WEDNESDAY:
week = "星期三";
break;
case DateTimeConstants.THURSDAY:
week = "星期四";
break;
case DateTimeConstants.FRIDAY:
week = "星期五";
break;
case DateTimeConstants.SATURDAY:
week = "星期六";
default:
break;
return week;
/**
* 获取指定时间是一周的星期几
* @param year
* @param month
* @param day
* @return
*/
public static String getWeek(Integer year, Integer month, Integer day)
LocalDate dts = new LocalDate(year, month, day);
String week = null;
switch (dts.getDayOfWeek())
case DateTimeConstants.SUNDAY:
week = "星期日";
break;
case DateTimeConstants.MONDAY:
week = "星期一";
break;
case DateTimeConstants.TUESDAY:
week = "星期二";
break;
case DateTimeConstants.WEDNESDAY:
week = "星期三";
break;
case DateTimeConstants.THURSDAY:
week = "星期四";
break;
case DateTimeConstants.FRIDAY:
week = "星期五";
break;
case DateTimeConstants.SATURDAY:
week = "星期六";
break;
default:
break;
return week;
/**
* 计算两个时间相差多少天
* @param startDate
* @param endDate
* @return
*/
public static Integer diffDay(Date startDate, Date endDate)
if (startDate == null || endDate == null)
return null;
DateTime dt1 = new DateTime(startDate);
DateTime dt2 = new DateTime(endDate);
int day = Days.daysBetween(dt1, dt2).getDays();
return Math.abs(day);
参考链接
Java第三方库JodaTime的具体使用是怎样的_编程设计_IT干货网
以上是关于Java -- JodaTime第三方库操作时间的主要内容,如果未能解决你的问题,请参考以下文章
我应该使用 Java 日期和时间类还是使用像 Joda Time 这样的 3rd 方库?
鸿蒙开源第三方组件——日期和时间处理组件JodaTime-ohos
Java - 使用DBUtils BeanListHandler将查询中的所有日期转换为JodaTime的DateTime