Java 中日期的几种常见操作 —— 取值、转换、加减、比较

时间:2022-06-12 14:38:38

Java 的开发过程中免不了与 Date 类型纠缠,准备总结一下项目经常使用的日期相关操作,JDK 版本 1.7。

1. 日期取值

在旧版本 JDK 的时代,有不少代码中日期取值利用了 java.util.Date 类,但是由于 Date 类不便于实现国际化,其实从 JDK1.1 开始,就更推荐使用 java.util.Calendar 类进行时间和日期方面的处理。这里便不介绍 Date 类的操作,让我们直奔主题吧,如何利用 Calendar 类取得现在的日期时间。

由于 Calendar 的构造器方法被 protected 修饰,所以我们会通过 API 中提供的 getInstance 方法来创建 Calendar 对象。

//有多个重载方法创建 Calendar 对象
Calendar now = Calendar.getInstance(); //默认
//指定时区和地区,也可以只输入其中一个参数
Calendar now = Calendar.getInstance(timeZone, locale);

然后我们就可以通过该对象取得当前的各种时间参数了。

int year = now.get(Calendar.YEAR); //2015,当前年份
int month = now.get(Calendar.MONTH) + 1; //12,
当前月,注意加 1
int day = now.get(Calendar.DATE); //23,当前日
Date date = now.getTime(); //直接取得一个 Date 类型的日期

要取得其他类型的时间数据仅需修改 now.get() 内的参数,除了以上三种参数,其他常用参数如下:

  • Calendar.DAY_OF_MONTH:日期,和 Calendar.DATE 相同
  • Calendar.HOUR:12 小时制的小时数
  • Calendar.HOUR_OF_DAY:24小时制的小时数
  • Calendar.MINUTE:分钟
  • Calendar.SECOND:秒
  • Calendar.DAY_OF_WEEK:周几

除了取得时间数据,我们也可以通过 Calendar 对象设置各种时间参数。

//只设定某个字段的值
// public final void set(int field, int value)
now.set(Calendar.YEAR, 2016);
//设定年月日或者年月日时分或年月日时分秒
// public final void set(int year, int month, int date[, int hourOfDay, int minute, int second])
now.set(2016, 1, 1[, 11, 1, 1]);
//直接传入一个 Date 类型的日期
// public final void setTime(Date date)
now.set(date);

注意:

  • 当设置了时间参数后,其他相关的数值都会重新计算,例如当你把日期设为 11 号后,周几就会作对应变化。
  • 获得的月份加 1 才是实际月份。
  • 在 Calendar 类中,周日是 1,周一是 2,以此类推。

2. 日期转换

聊完日期取值,接下来聊聊日期转换,转换一般是 Date 型日期String 型字符串之间的相互转换,我主要利用 java.text.SimpleDateFormat进行转换操作。

SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
try {
//日期转字符串
Calendar calendar = Calendar.getInstance();
Date
date = calendar.getTime();
String dateStringParse = sdf.format(
date);
//字符串转日期
String dateString = "2016-01-01 11:11:11";
Date dateParse = sdf.parse(dateString);
} catch (ParseException e) {
e.printStackTrace();
}

注意:

  • 创建 SimpleDateFormat 对象时必须指定转换格式。
  • 转换格式区分大小写,yyyy 代表年份,MM 代表月份,dd 代表日期,HH 代表 24 进制的小时,hh 代表 12 进制的小时,mm 代表分钟,ss 代表秒。

3. 日期加减

通常来说,我们会对日期做两种加减操作:

以某个日期为基准,计算其几天前/后、几年前/后,或者其他时间单位前后的日期

//根据现在时间计算
Calendar now = Calendar.getInstance();
now.add(Calendar.YEAR, 1); //现在时间的1年后
now.add(Calendar.YEAR, -1); //现在时间的1年前

//根据某个特定的时间 date (Date 型) 计算
Calendar specialDate = Calendar.getInstance();
specialDate.setTime(date); //注意在此处将 specialDate 的值改为特定日期
specialDate.add(Calendar.YEAR, 1); //特定时间的1年后
specialDate.add(Calendar.YEAR, -1); //特定时间的1年前

注意使用了 Calendar 对象的 add 方法,可以更改 Calendar.YEAR 为任意时间单位字段,完成各种时间单位下的日期计算。

计算两个时间的间隔,例如计算 2016 年 1 月 1 日距离现在有多少天。

SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
String dateString = "2016-01-01 11:11:11";
Calendar calendar = Calendar.getInstance();
long
nowDate = calendar.getTime().getTime(); //Date.getTime() 获得毫秒型日期
try {
long
specialDate = sdf.parse(dateString).getTime();
long betweenDate = (specialDate - nowDate) / (1000 * 60 * 60 * 24);
//计算间隔多少天,则除以毫秒到天的转换公式
System.out.print(betweenDate);
} catch (ParseException e) {
e.printStackTrace();
}

4. 日期比较

翻看自己以前的代码,发现每当进行日期比较的操作时,总会先将日期转为 “yyyyMMdd” 格式的字符串,再将字符串转为数值,然后比较数值大小。哈哈,一个简单的比较操作,却要写十几行代码,有点目不忍视。现在得说说正确地日期比较姿势是怎么样的。

日期比较一般有两种方法,对于 java.util.Date 或者 java.util.Calendar 都是通用的。一种是通过 after() 与 before() 方法进行比较,一种是通过 compareTo() 方法进行比较。

SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
String dateString_01 = "2016-01-01 11:11:11";
String dateString_02 = "2016-01-02 11:11:11";
try {
Date date_01 = sdf.parse(dateString_01);
Date date_02 = sdf.parse(dateString_02);
System.out.println(date_01.before(date_02)); //true,当 date_01 小于 date_02 时,为 true,否则为 false
System.out.println(date_02.after(date_01)); //true,当 date_02 大于 date_01 时,为 true,否则为 false
System.out.println(date_01.compareTo(date_02)); //-1,当 date_01 小于 date_02 时,为 -1
System.out.println(date_02.compareTo(date_01)); //1,当 date_02 大于 date_01 时,为 1
System.out.println(date_02.compareTo(date_02)); //0,当两个日期相等时,为 0
} catch (ParseException e) {
e.printStackTrace();
}