Java开发笔记(四十二)日历工具的常见应用
前面介绍了日历工具calendar的基本用法,乍看起来calendar与date两个半斤八两,似乎没有多大区别,那又何苦庸人自扰鼓捣一个新玩意呢?显然这样小瞧了calendar,其实它的作用大着呢,接下来不妨深入探讨一下calendar的几种实际应用,主要包括:calendar和date类型互相转换、计算两个日历时间的天数、打印当前月份的月历等,分别说明如下。
1、calendar和date类型互相转换
虽说date早就应该被calendar取代,但毕竟是前辈,而且java也一直没有抛弃它,特别有一点:date拥有搭配的日期格式化工具simpledateformat,可以很方便地输出指定格式的日期时间字符串,敢问calendar有此绝活么?既然calendar无法覆盖date的所有功能,那就必须支持互相转换calendar和date类型,从而让日期实例去执行日历实例所不能完成的任务。因为类型转换的要求是calendar提出来的,所以这个转换动作理应由它实现,这里用到了calendar的gettime方法和settime方法,其中gettime方法的返回值就是date类型的实例,而settime方法可将date实例填入calendar实例。下面是通过gettime和settime方法转换日期类型和日历类型的代码例子:
// 把calendar类型的数据转换为date类型
private static void convertcalendartodate() {
// 创建一个日历实例
calendar calendar = calendar.getinstance();
// 调用日历实例的gettime方法,获得日期信息
date date = calendar.gettime();
system.out.println("convertcalendartodate date=" + date.tostring() + ", calendar=" + calendar.tostring());
}
// 把date类型的数据转换为calendar类型
private static void convertdatetocalendar() {
// 创建一个日历实例
calendar calendar = calendar.getinstance();
// 创建一个日期实例
date date = new date();
// 调用日历实例的settime方法,设置日期信息
calendar.settime(date);
system.out.println("convertdatetocalendar date=" + date.tostring() + ", calendar=" + calendar.tostring());
}
2、计算两个日历时间的天数
根据两个给定的时间,计算二者间隔的天数,这个业务场景也很常见。例如为了安全起见,网站每隔若干天就要求用户重新登录;又如信用卡还款,银行需要在还款日之前多少天提醒用户等等。这时用到了calendar的gettimeinmillis方法,该方法可返回毫秒计量的时间总数,只要把两个日历实例的时间总数相减,再把二者的差额从毫秒单位换算成以天为单位,即可求得这两个日历时间之间的天数。据此编写的计算方法代码如下所示:
// 计算两个日历实例间隔的天数
private static void countdays() {
calendar calendara = calendar.getinstance();
// 设置第一个日历实例的年月日
calendara.set(2018, 3, 15);
calendar calendarb = calendar.getinstance();
// 设置第二个日历实例的年月日
calendarb.set(2018, 9, 15);
// 获得第一个日历实例包含的时间总数(单位毫秒)
long timeofa = calendara.gettimeinmillis();
// 获得第二个日历实例包含的时间总数(单位毫秒)
long timeofb = calendarb.gettimeinmillis();
// 先计算二者的差额,再把毫秒计量的差额转换为天数
long daycount = (timeofb-timeofa)/(1000*60*60*24);
system.out.println("daycount="+daycount);
}
3、打印当前月份的月历
对于期待周末的学生和上班族来说,一份安排妥当的月历是必不可少的,现在利用calendar功能便能制作一个简单的月历。月历的每行均为一个星期,行首是星期一,行尾是星期日,然后分行打印当月从1号到月末的所有日子。其中的年、月、星期都是明确的,唯有月末的日子是变化着的,比如1、3、5、7、8、10、12这七个月的月末是31号,4、6、9、11这四个月的月末是30号,2月每逢闰年有29天、其它年份则有28天。倘若为了确定当月的最后一天,就得自己编码判断这些繁复的细节,可谓是绞尽脑汁、伤筋动骨。所幸calendar早已提供了getactualmaximum方法,该方法用于获得指定时间单位的最大合法值,如果指定的时间单位是calendar.date,则该方法的返回值就为当月的最后一天。于是获取月末日子的代码仅需下列一行而已:
// 获取当月的最后一天
int lastday = calendar.getactualmaximum(calendar.date);
这下月历具备的所有要素都集齐了,包括当前年份、当前月份、当月1号、当月最后一天,再把中间的日子分星期依次排列,一个简洁朴素的月历便出炉了。下面是使用日历工具计算并打印当前月历的代码例子:
// 打印当前月份的月历
private static void printmonthcalendar() {
// 创建一个日历实例
calendar calendar = calendar.getinstance();
// 设置日期为当月1号
calendar.set(calendar.date, 1);
// 获得该日期对应的星期几
int dayofweek = calendar.get(calendar.day_of_week);
dayofweek = dayofweek==1 ? 7 : dayofweek-1;
// 获取当月的最后一天
int lastday = calendar.getactualmaximum(calendar.date);
// 拼接月历开头的年月
string yearandmonth = string.format("\n %d年%d月",
calendar.get(calendar.year), calendar.get(calendar.month)+1);
system.out.println(yearandmonth);
system.out.println(" 星期一 星期二 星期三 星期四 星期五 星期六 星期日");
// 先补齐1号前面的空白
for (int i=1; i<dayofweek; i++) {
system.out.print(" ");
}
// 循环打印从一号到本月最后一天的日子
for (int i=1; i<=lastday; i++) {
string today = string.format("%7d", i);
system.out.print(today);
// 如果当天是星期日,末尾就另起一行
if ((dayofweek+i-1)%7 == 0) {
system.out.println();
}
}
}
运行上述的月历代码,观察到的打印结果如下图所示。
更多java技术文章参见《java开发笔记(序)章节目录》
上一篇: 支付宝app怎么使用蚂蚁会员88积分赢1212红包?
下一篇: 如何监控Redis性能指标(译)