1. Java时间戳

在最早出现的 UNIX 操作系统考虑到计算机产生的年代和应用的时限,把1970年1月1日0点定义为时间纪元,这种定义时间的方式在计算机语言中广泛存在,Java就是其中之一。之所以使用Long数据类型来表示时间是因为Long类型可以表示足够大的数,进而可以表示未来更多的时间。

2. Java中日期时间的使用

主要涉及一下几个类:

java.util.Date
java.text.DateFormat
java.text.SimpleDateFormat
java.util.Calendar
java.util.GregorianCalendar

下面是对上述几个类逐个介绍:

2.1 java.util.Date

先看Java jdk文档的描述:

The class Date represents a specific instant in time, with millisecond precision.

意思是说Data类表示一个特定的时间瞬间,精确到毫秒。并且从 JDK 1.1 起,废弃了把日期转换为年、月、日、小时、分钟和秒值的方法,应该使用 Calendar 类实现日期和时间各字段之间的转换,使用 DateFormat 类来格式化和分析日期字符串。其实Date里的好多方法现在都已经被废弃。

例子:

public class DateDemo {
    public static void main(String[] args) {
        Date date = new Date();
        String current = date.toString();
        System.out.println("当前时间是:"+current);

        long millisecond =  date.getTime();
        System.out.println("自格林威治时间(1970年1月1日0时0分0秒)起到现在的所经过的毫秒数:"+millisecond);

        //setTime(long time)方法设置自日期1970年1月1日00:00:00 GMT后,来显示时间的毫秒。
        date.setTime(1234567890);
        System.out.println("设置后的时间为:"+date.toString());

        //比较一个时间是否在另一个时间之前
        Date date1 = new Date();
        date1.setTime(12345);
        Date date2 = new Date();
        date2.setTime(1234);
        System.out.println("date1 在 date2 之前:"+date1.before(date2));
        System.out.println("date1 在 date2 之后:"+date1.after(date2));
    }
}

java 对接exchange 日历 java 日历类_System

2.2 java.text.DateFormat

先看一下继承体系:

java 对接exchange 日历 java 日历类_java_02


DateFormat是个抽象类,我们使用的其实是的直接子类SimpleDateFormat。

DateFormat 是日期/时间格式化子类的抽象类,它以与语言无关的方式格式化并解析日期或时间。日期/时间格式化子类(如 SimpleDateFormat)允许进行格式化(也就是日期 -> 文本)、解析(文本-> 日期)和标准化。将日期表示为 Date 对象,或者表示为从 GMT(格林尼治标准时间)1970 年 1 月 1 日 00:00:00 这一刻开始的毫秒数。

(1) DateFormat 提供了很多类方法,以获得基于默认或给定语言环境和多种格式化风格的默认日期/时间 Formatter。格式化风格包括 FULL、LONG、MEDIUM 和 SHORT。方法描述中提供了使用这些风格的更多细节和示例。
(2) DateFormat 可帮助进行格式化并解析任何语言环境的日期。对于月、星期,甚至日历格式(阴历和阳历),其代码可完全与语言环境的约定无关。
要格式化一个当前语言环境下的日期,可使用某个静态工厂方法:如

myString = DateFormat.getDateInstance().format(myDate);

(3) 如果格式化多个日期,那么获取该格式并多次使用它是更为高效的做法,这样系统就不必多次获取有关环境语言和国家/地区约定的信息了。

DateFormat df = DateFormat.getDateInstance();
for (int i = 0; i < myDate.length; ++i) {
    output.println(df.format(myDate[i]) + "; ");
}

(4)要格式化不同语言环境的日期,可在 getDateInstance() 的调用中指定它,如:

DateFormat df = DateFormat.getDateInstance(DateFormat.LONG, Locale.FRANCE);

还可使用 DateFormat 进行解析。

myDate = df.parse(myString);

(5) 使用 getDateInstance 来获取该国家/地区的标准日期格式。另外还提供了一些其他静态工厂方法。使用 getTimeInstance 可获取该国家/地区的时间格式。使用 getDateTimeInstance 可获取日期和时间格式。可以将不同选项传入这些工厂方法,以控制结果的长度(从 SHORT 到 MEDIUM 到 LONG 再到 FULL)。确切的结果取决于语言环境,但是通常:

SHORT 完全为数字,如 12.13.52 或 3:30pm
MEDIUM 较长,如 Jan 12, 1952
LONG 更长,如 January 12, 1952 或 3:30:32pm
FULL 是完全指定,如 Tuesday、April 12、1952 AD 或 3:30:42pm PST。

如果愿意,还可以在格式上设置时区。如果想对格式化或解析施加更多的控制(或者给予用户更多的控制),可以尝试将从工厂方法所获取的 DateFormat 强制转换为 SimpleDateFormat。这适用于大多数国家/地区;只是要记住将其放入一个 try 代码块中,以防遇到特殊的格式。

还可以使用借助 ParsePosition 和 FieldPosition 的解析和格式化方法形式来逐步地解析字符串的各部分。
对齐任意特定的字段,或者找出字符串在屏幕上的选择位置。

同步

日期格式不是同步的。建议为每个线程创建独立的格式实例。如果多个线程同时访问一个格式,则它必须保持外部同步。

例子:
public static void dateFormatTest(){
        Date date = new Date();
        DateFormat fullFormat = DateFormat.getDateTimeInstance(DateFormat.FULL, DateFormat.FULL);
        DateFormat longFormat = DateFormat.getDateTimeInstance(DateFormat.LONG, DateFormat.LONG);
        DateFormat mediumFormat = DateFormat.getDateTimeInstance(DateFormat.MEDIUM, DateFormat.MEDIUM);
        DateFormat shortFormat = DateFormat.getDateTimeInstance(DateFormat.SHORT, DateFormat.SHORT);

        System.out.println("DateFormat.FULL   = "+fullFormat.format(date));
        System.out.println("DateFormat.LONG   = "+longFormat.format(date));
        System.out.println("DateFormat.MEDIUM = "+mediumFormat.format(date));
        System.out.println("DateFormat.SHORT  = "+shortFormat.format(date));

        DateFormat dateFormat = DateFormat.getDateInstance();
        String myString = dateFormat.format(new Date());
        System.out.println("myString = "+myString);

        DateFormat dateFormat1 = DateFormat.getDateInstance(DateFormat.DATE_FIELD);
        System.out.println("DateFormat.DATE_FIELD = "+dateFormat1.format(date));

    }

java 对接exchange 日历 java 日历类_java 对接exchange 日历_03

2.3 java.text.SimpleDateFormat的使用

java 对接exchange 日历 java 日历类_java 对接exchange 日历_04

SimpleDateFormat 是一个以与语言环境有关的方式来格式化和解析日期的具体类。它允许进行格式化(日期 -> 文本)、解析(文本 -> 日期)和规范化。

SimpleDateFormat 使得可以选择任何用户定义的日期-时间格式的模式。但是,仍然建议通过 DateFormat 中的 getTimeInstance、getDateInstance 或 getDateTimeInstance 来创建日期-时间格式器。每一个这样的类方法都能够返回一个以默认格式模式初始化的日期/时间格式器。可以根据需要使用 applyPattern 方法来修改格式模式。

日期和时间模式

日期和时间格式由日期和时间模式 字符串指定。在日期和时间模式字符串中,未加引号的字母 ‘A’ 到 ‘Z’ 和 ‘a’ 到 ‘z’ 被解释为模式字母,用来表示日期或时间字符串元素。文本可以使用单引号 (‘) 引起来,以免进行解释。””” 表示单引号。所有其他字符均不解释;只是在格式化时将它们简单复制到输出字符串,或者在解析时与输入字符串进行匹配。

定义了以下模式字母(所有其他字符 ‘A’ 到 ‘Z’ 和 ‘a’ 到 ‘z’ 都被保留):

java 对接exchange 日历 java 日历类_System_05


来上个例子吧

public static void simpleDateFormatTest(){
        SimpleDateFormat simpleDateFormat1 =new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        SimpleDateFormat simpleDateFormat2 =new SimpleDateFormat("yyyy年MM月dd日 HH时mm分ss秒");
        SimpleDateFormat simpleDateFormat3 =new SimpleDateFormat("这个一天中的第 H 个小时");
        SimpleDateFormat simpleDateFormat4 =new SimpleDateFormat("这是一年中的第 D 天");
        SimpleDateFormat simpleDateFormat5 =new SimpleDateFormat("这是 z 时区");
        SimpleDateFormat simpleDateFormat6 =new SimpleDateFormat("这是一年中的第 M 个星期");

        Date date =new Date();
        System.out.println(date.toString());
        System.out.println(simpleDateFormat1.format(date));
        System.out.println(simpleDateFormat2.format(date));
        System.out.println(simpleDateFormat3.format(date));
        System.out.println(simpleDateFormat4.format(date));
        System.out.println(simpleDateFormat5.format(date));
        System.out.println(simpleDateFormat6.format(date));
    }

java 对接exchange 日历 java 日历类_java_06

2.4 java.util.Calendar

继承图:

java 对接exchange 日历 java 日历类_java 对接exchange 日历_07

Calendar 类是一个抽象类,它为特定瞬间与一组日历字段(诸如YEAR、MONTH、DAY_OF_MONTH、HOUR等)之间的转换提供了一些方法,并为操作日历字段(例如获得下星期的日期)提供了一些方法。瞬间可用毫秒值来表示,它是距历元(即格林威治标准时间 1970年1月1日的00:00:00.000,格里高利历)的偏移量。

自从JDK1.1版本开始,系统推荐使用Calendar类进日期和时间的处理。
java.util.calendar 类是一个抽象类,它提供了与在某一特定时刻和一组日历字段如YEAR,MONTH,DAY_OF_MONTH,HOUR等,并为操作日历字段。

public static void calendarTest(){
        Calendar c1 = Calendar.getInstance();
        c1.set(2016, 11 - 1, 11);
        System.out.println("上述设置的时间为:" + c1.getTime());

        Calendar c2 = Calendar.getInstance();
        int year = c2.get(Calendar.YEAR);
        int month = c2.get(Calendar.MONTH) + 1;
        int date = c2.get(Calendar.DATE);
        int day = c2.get(Calendar.DAY_OF_WEEK);
        int hour = c2.get(Calendar.HOUR_OF_DAY);
        int minute = c2.get(Calendar.MINUTE);
        int second = c2.get(Calendar.SECOND);

        System.out.println("当前年份:" + year);
        System.out.println("当前月份:" + month);
        System.out.println("当前日期:" + date);
        System.out.println("当前星期:" + day);
        System.out.println("当前小时:" + hour);
        System.out.println("当前分钟:" + minute);
        System.out.println("当前秒:" + second);
    }

java 对接exchange 日历 java 日历类_字符串_08

2.5 java.util.GregorianCalendar

GregorianCalendar继承自Calendar,扩展了一个更加通用的Calendar类,用来表示标准的日历,这个类描述了日历的一般属性,提供了世界上大多数国家和地区使用的标准日历。

来个例子吧:

public static void gregorianCalendarTest(){
        GregorianCalendar gregorianCalendar1 = new GregorianCalendar();
        int today = gregorianCalendar1.get(Calendar.DAY_OF_MONTH);
        int month = gregorianCalendar1.get(Calendar.MONTH);
        int weekday = gregorianCalendar1.get(Calendar.DAY_OF_WEEK);
        int firstDayOfWeek = gregorianCalendar1.getFirstDayOfWeek();
        System.out.println("------------------------------------------");
        System.out.println("当前时间为:"+gregorianCalendar1.getTime());
        System.out.println("today = " + today);
        System.out.println("month = " + month+1);// month是从0开始,
        System.out.println("weekday = " + weekday);
        System.out.println("每周第一天从"+firstDayOfWeek+"开始");

        //设置日期
        GregorianCalendar gregorianCalendar2 = new GregorianCalendar();
        //calendar.set()设置日期
        // month是从0开始,
        gregorianCalendar2.set(2015, 11, 12, 10, 21, 20);
        System.out.println("------------------------------------------");
        System.out.println("设置的时间为:" + gregorianCalendar2.getTime());

        //日期类转化成时间类
        Calendar gregorianCalendar3 = new GregorianCalendar();
        System.out.println("------------------------------------------");
        System.out.println("当前时间为:"+gregorianCalendar3.getTime());
        //年份减去2年
        gregorianCalendar3.add(Calendar.YEAR, -2);
        //月份减去2年
        gregorianCalendar3.add(Calendar.MONTH, -2);
        //日期减去两天
        gregorianCalendar3.add(Calendar.DATE, -2);
        System.out.println("修改过的时间为:"+gregorianCalendar3.getTime());
    }

java 对接exchange 日历 java 日历类_java 对接exchange 日历_09

笔者水平有限,如有错误,欢迎指正,谢谢!