public class Date
extends Object
implements Serializable, Cloneable, Comparable<Date>
Date类的使用
在JDK 1.1之前, Date
有两个附加功能。 它允许将日期解释为年,月,日,小时,分钟和第二个值。 它还允许格式化和解析日期字符串。 不幸的是,这些功能的API不适合国际化。 从JDK 1.1开始, Calendar
类应该用于在日期和时间字段之间进行转换,并且DateFormat
类应用于格式化和解析日期字符串。 在相应的方法Date
被弃用。
尽管Date
类旨在反映协调的世界时间(UTC),但根据Java虚拟机的主机环境的不同,可能不会这样做。 几乎所有的现代操作系统都假设在所有情况下1天= 24×60×60 = 86400秒。 然而,在UTC的时候,大概每一两年会有一秒钟的时间,叫做“闰秒”。 闰秒总是作为一天的最后一秒,总是在12月31日或6月30日。例如,1995年的最后一分钟是61秒,由于增加了闰秒。 大多数计算机时钟不够准确,不能反映出闰秒的区别。
一些计算机标准是根据格林尼治标准时间(GMT)定义的,相当于世界时间(UT)。 GMT是标准的“民用”名称; UT是同一标准的“科学”名称。 UTC和UT之间的区别是UTC是基于原子钟,UT是基于天文观测,对于所有的实际目的来说,这是一个看不见的细毛。 因为地球的旋转不均匀(减速并以复杂的方式加速),UT并不总是均匀地流动。 根据需要,将时差引入到UTC中,以使UT在UT1的0.9秒内保持UTC,这是UT的版本,并应用了某些修正。 还有其他的时间和日期系统; 例如,基于卫星的全球定位系统(GPS)使用的时间尺度与UTC同步,但不对闰秒进行调整。
在类的所有方法Date
接收或返回年,月,日,小时,分钟和秒值,以下表述中使用:
- y年代表整数y
- 1900
。 - 一个月由0到11的整数表示; 0是1月,1是2月,等等; 11月12日。
- 日期(月的一天)以通常的方式从1到31的整数表示。
- 一小时由0到23之间的整数表示。因此,从午夜到凌晨1点的时间是小时0,从中午到下午1点的小时是12小时。
- 一般以0?59的整数表示。
- 第二个由0到61的整数表示; 值60和61仅发生在闰秒上,甚至仅在实际上正确跟踪闰秒的Java实现中发生。 由于目前引入闰秒的方式,在同一分钟内不会发生两个闰秒,但是本规范遵循ISO C的日期和时间约定。
在所有情况下,为这些目的而提供的方法的论证不必在指定范围内; 例如,可以将日期指定为1月32日,并将其解释为2月1日。
public class GetTime {
//调用系统内部的时间格式;public static void main(String[] args) {Date date=new Date();System.out.println("默认时间的格式:"+date);System.out.println("两位24小时制的小时:"+String.format("%tH", date));System.out.println("两位12小时制的小时:"+String.format("%tl", date));System.out.println("24制的小时:"+String.format("%tk", date));System.out.println("12制的小时:"+String.format("%tl", date));System.out.println("两位小时中的分钟:"+String.format("%tM", date));System.out.println("两位分钟的中秒:"+String.format("%tS", date));System.out.println("表示时区缩写形式:"+String.format("%tZ", date));System.out.println("上午还是下午:"+String.format("%tp", date));System.out.println("日期时间组合格式化:");System.out.println("默认时间的格式:"+date);System.out.println("24小时制的时间,被格式化为小时和分钟:"+String.format("%tR", date));System.out.println("24小时制的时间,被格式化为小时和分钟,秒"+String.format("%tT", date));System.out.println("12制的时间:"+String.format("%tr", date));System.out.println("日期被格式化:"+String.format("%tD", date));System.out.println("ISO 8601格式的完整日期:"+String.format("%tF", date));System.out.println("日期和时间格式化为:"+String.format("%tc", date));}}
//调用系统内部的 一些方式:public static void main(String[] args) {Date today=new Date();String a=String.format(Locale.US, "%tb", today);String b=String.format(Locale.US, "%tB", today);String c=String.format("%ta", today);//指定语言中的星期几的简称String d=String.format("%tA", today);//指定语言中的星期几的全称String e=String.format("%tY", today);//四位年份String f=String.format("%ty", today);//两位年份String g=String.format("%tm", today);//月份String h=String.format("%td", today);//一个月中的第几天String i=String.format("%te", today);//一个月中的某一天String k=String.format("%tc", today);//包括全部的日期和时间String l=String.format("%tj", today);//一年中的第几天System.out.println("格式化后的字符串的英文缩写:"+a);System.out.println("格式化后的字符串的英文全写:"+b);System.out.println("月格式化后的字符串为星期:"+c);System.out.println("格式化后的字符串为星期:"+d);System.out.println("格式化后的字符串为4位的年份值:"+e);System.out.println("格式化后的字符串为4位的年份值:"+f);System.out.println("格式化后的字符串为2位的月份值:"+g);System.out.println("格式化后的字符串为2位的日期值:"+h);System.out.println("格式化后的字符串为1位的日期值:"+i);System.out.println("日期值:"+k);System.out.println("当年中的第几天:"+l);}
日期比较
Java使用以下三种方法来比较两个日期:
- 使用 getTime() 方法获取两个日期(自1970年1月1日经历的毫秒数值),然后比较这两个值。
- 使用方法 before(),after() 和 equals()。例如,一个月的12号比18号早,则 new Date(99, 2, 12).before(new Date (99, 2, 18)) 返回true。
- 使用 compareTo() 方法,它是由 Comparable 接口定义的,Date 类实现了这个接口。
DateFormat类:
DateFormat
是日期/时间格式化子类的抽象类,它以语言无关的方式格式化和分析日期或时间。 日期/时间格式化子类(如SimpleDateFormat
)允许格式化(即日期文本),解析(文本日期)和归一化。 该日期表示为一个Date
对象,或自1970年1月1日00:00:00 GMT以来的毫秒。
DateFormat
提供了许多类方法,用于根据默认或给定的区域设置和多个格式化样式获取默认的日期/时间格式化程序。 格式化风格包括FULL
, LONG
, MEDIUM
和SHORT
。 方法说明中提供了更多细节和使用这些样式的示例。
DateFormat
可帮助您格式化和解析任何区域设置的日期。 您的代码可以完全独立于几个月,几个星期甚至日历格式的区域设置约定:月球与太阳能。
要格式化当前区域设置的日期,请使用静态工厂方法之一:
myString = DateFormat.getDateInstance().format(myDate);
如果要格式化多个日期,更多的是获取格式并多次使用它,以便系统不必多次获取有关本地语言和国家/地区约定的信息。
DateFormat df = DateFormat.getDateInstance();for (int i = 0; i < myDate.length; ++i) {output.println(df.format(myDate[i]) + "; ");}
要格式化不同语言环境的日期,请在调用getDateInstance()
中指定。
DateFormat df = DateFormat.getDateInstance(DateFormat.LONG, Locale.FRANCE);
您也可以使用DateFormat进行解析。
myDate = df.parse(myString);
使用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 or 3:30:42pm PST
。
您也可以根据需要设置格式的时区。 如果你想在格式或分析更精确的控制,(或者希望给用户更多的控制),可以尝试铸造DateFormat
你从工厂方法到获得SimpleDateFormat
。 这将适用于大多数国家; 只要记住把它放在一个try
块中,以防万一你遇到不寻常的一个。
以下代码是对这些的简单使用具体的可以查看API:
public static void main(String[] args) {Date p=new Date();p.getTime();//System.out.println(p.getTime());
//date Format类
// 美式
// 日期DateFormat df1=DateFormat.getDateInstance();String string=df1.format(new Date());System.out.println(string);
// 日期和时间一起显示精确到秒DateFormat df2=DateFormat.getDateTimeInstance();System.out.println(df2.format(new Date()));
// 中式
// 年日期DateFormat df3=DateFormat.getDateInstance(DateFormat.YEAR_FIELD,new Locale("zh","CN"));System.out.println(df3.format(new Date()));
// 年月日上下午秒DateFormat df4=DateFormat.getDateTimeInstance(DateFormat.YEAR_FIELD,DateFormat.ERA_FIELD,new Locale("zh","CN"));System.out.println(df4.format(new Date()));
// simpleDateFormate类Date now=new Date();String s="北京时间:yyy年MM月dd日,E,HH:mm:ss";SimpleDateFormat f=new SimpleDateFormat(s);System.out.println(f.format(now));}
SimpleDateFormat:
SimpleDateFormat
是一个具体的类,用于以区域设置敏感的方式格式化和解析日期。 它允许格式化(日期文本),解析(文本日期)和归一化。
SimpleDateFormat
允许您从选择日期时间格式化的任何用户定义的模式开始。 不过,建议您创建一个日期-时间格式有两种getTimeInstance
, getDateInstance
,或getDateTimeInstance
在DateFormat
。 这些类方法中的每一个都可以返回使用默认格式模式初始化的日期/时间格式化程序。 您可以根据需要使用applyPattern
方法修改格式模式。 有关使用这些方法的更多信息,请参见DateFormat
。
日期和时间模式
日期和时间格式由日期和时间模式字符串指定。 在日期和时间模式字符串中,从'A'
到'Z'
和从'a'
到'z'
的非引号的字母被解释为表示日期或时间字符串的组件的模式字母。 可以使用单引号( '
)引用文本,以避免解释。 "''"
代表单引号。 所有其他字符不被解释; 在格式化过程中,它们只是复制到输出字符串中,或者在解析过程中与输入字符串匹配。
定义了以下图案字母(所有其他字符从'A'
到'Z'
和从'a'
到'z'
被保留):
Letter Date or Time Component Presentation Examples G
Era designator Text AD
y
Year Year 1996
;96
Y
Week year Year 2009
;09
M
Month in year (context sensitive) Month July
;Jul
;07
L
Month in year (standalone form) Month July
;Jul
;07
w
Week in year Number 27
W
Week in month Number 2
D
Day in year Number 189
d
Day in month Number 10
F
Day of week in month Number 2
E
Day name in week Text Tuesday
;Tue
u
Day number of week (1 = Monday, ..., 7 = Sunday) Number 1
a
Am/pm marker Text PM
H
Hour in day (0-23) Number 0
k
Hour in day (1-24) Number 24
K
Hour in am/pm (0-11) Number 0
h
Hour in am/pm (1-12) Number 12
m
Minute in hour Number 30
s
Second in minute Number 55
S
Millisecond Number 978
z
Time zone General time zone Pacific Standard Time
;PST
;GMT-08:00
Z
Time zone RFC 822 time zone -0800
X
Time zone ISO 8601 time zone -08
;-0800
;-08:00
模式字母通常重复,因为它们的数字确定了准确的表示:
- Text:对于格式化,如果模式字母的数量是4以上,则使用完整的形式; 否则,如果有的话,使用简短或缩写形式。 对于解析,两种形式都是接受的,与模式字母的数量无关。
- Number:对于格式化,模式字母的数量是最小位数,而较短的数字将零填充到此数量。 对于解析,模式字母的数量将被忽略,除非需要分隔两个相邻的字段。
- Year:如果格式化程序的
Calendar
是公历,则应用以下规则。- 对于格式化,如果模式字母数为2,那么年份将被截断为2位数; 否则被解释为number 。
- 对于解析,如果模式字母的数量大于2,则年份将按字面解释,而不管数字的数量。 所以使用“MM / dd / yyyy”模式,“01/11/12”解析到公元12年1月11日
- 为了使用缩写年份模式(“y”或“yy”)进行解析,
SimpleDateFormat
必须解释相对于某个世纪的缩写年份。 它是通过将日期调整为在创建SimpleDateFormat
实例之后的80年之前和20年之后进行的。 例如,使用1997年1月1日创建的“MM / dd / yy”模式和SimpleDateFormat
实例,字符串“01/11/12”将被解释为2012年1月11日,而字符串“05/04 / 64“将被解释为1964年5月4日。在解析期间,只有由Character.isDigit(char)
定义的两个数字组成的字符串将被解析为默认世纪。 任何其他数字字符串,例如一位数字字符串,三位或三位以上数字字符串,或两位数字字符串(不全部为数字)(例如“-1”),均按字面解释。 所以“01/02/3”或“01/02/003”的解析方式与公元3年1月2日相同。 同样,“01/02 / -3”在公元前4年1月2日被解析。
如果周年'Y'
被指定,并且calendar不支持任何week years ,则使用日历年('y'
)。 可以通过致电getCalendar()
测试周年的支持。isWeekDateSupported()
。
- Month:如果模式字母数为3以上,则该月份被解释为text ; 否则,它被解释为number 。
- 字母M产生上下文相关的月份名称,例如嵌入的名称形式。 如果
DateFormatSymbols
已经与构造明确设置SimpleDateFormat(String, DateFormatSymbols)
或方法setDateFormatSymbols(DateFormatSymbols)
,由给定月份名称DateFormatSymbols
被使用。 - L字母生成独立形式的月份名称。
- 字母M产生上下文相关的月份名称,例如嵌入的名称形式。 如果
- General time zone:如果他们有姓名,时区将被解释为text 。 对于表示GMT偏移值的时区,
SimpleDateFormat
还支持本地化的日期和时间模式字符串。 在这些字符串中,上述的图案字母可以被替换为其他与区域相关的图案字母。 SimpleDateFormat
不处理除图案字母之外的文本的本地化;这取决于课堂的客户。
例子
以下示例显示如何在美国地区中解释日期和时间模式。 给定的日期和时间是2001-07-04 12:08:56当地时间在美国太平洋时间时区。
Date and Time Pattern Result "yyyy.MM.dd G 'at' HH:mm:ss z"
2001.07.04 AD at 12:08:56 PDT
"EEE, MMM d, ''yy"
Wed, Jul 4, '01
"h:mm a"
12:08 PM
"hh 'o''clock' a, zzzz"
12 o'clock PM, Pacific Daylight Time
"K:mm a, z"
0:08 PM, PDT
"yyyyy.MMMMM.dd GGG hh:mm aaa"
02001.July.04 AD 12:08 PM
"EEE, d MMM yyyy HH:mm:ss Z"
Wed, 4 Jul 2001 12:08:56 -0700
"yyMMddHHmmssZ"
010704120856-0700
"yyyy-MM-dd'T'HH:mm:ss.SSSZ"
2001-07-04T12:08:56.235-0700
"yyyy-MM-dd'T'HH:mm:ss.SSSXXX"
2001-07-04T12:08:56.235-07:00
"YYYY-'W'ww-u"
2001-W27-3
Synchronization
日期格式不同步。 建议为每个线程创建单独的格式实例。 如果多个线程同时访问格式,则必须在外部进行同步。
Calendar类
我们现在已经能够格式化并创建一个日期对象了,但是我们如何才能设置和获取日期数据的特定部分呢,比如说小时,日,或者分钟? 我们又如何在日期的这些部分加上或者减去值呢? 答案是使用Calendar 类。
Calendar类的功能要比Date类强大很多,而且在实现方式上也比Date类要复杂一些。
Calendar类是一个抽象类,在实际使用时实现特定的子类的对象,创建对象的过程对程序员来说是透明的,只需要使用getInstance方法创建即可。
创建一个代表系统当前日期的Calendar对象
Calendar c = Calendar.getInstance();//默认是当前日期
创建一个指定日期的Calendar对象
使用Calendar类代表特定的时间,需要首先创建一个Calendar的对象,然后再设定该对象中的年月日参数来完成。
//创建一个代表2009年6月12日的Calendar对象
Calendar c1 = Calendar.getInstance();
c1.set(2009, 6 - 1, 12);
Calendar类对象字段类型
Calendar类中用以下这些常量表示不同的意义,jdk内的很多类其实都是采用的这种思想
常量 | 描述 |
---|---|
Calendar.YEAR | 年份 |
Calendar.MONTH | 月份 |
Calendar.DATE | 日期 |
Calendar.DAY_OF_MONTH | 日期,和上面的字段意义完全相同 |
Calendar.HOUR | 12小时制的小时 |
Calendar.HOUR_OF_DAY | 24小时制的小时 |
Calendar.MINUTE | 分钟 |
Calendar.SECOND | 秒 |
Calendar.DAY_OF_WEEK | 星期几 |
Calendar类对象信息的设置
Set设置
如:
Calendar c1 = Calendar.getInstance();
调用:
public final void set(int year,int month,int date)
c1.set(2009, 6, 12);//把Calendar对象c1的年月日分别设这为:2009、6、12
利用字段类型设置
如果只设定某个字段,例如日期的值,则可以使用如下set方法:
public void set(int field,int value)
把 c1对象代表的日期设置为10号,其它所有的数值会被重新计算
c1.set(Calendar.DATE,10);
把c1对象代表的年份设置为2008年,其他的所有数值会被重新计算
c1.set(Calendar.YEAR,2008);
其他字段属性set的意义以此类推
Add设置
Calendar c1 = Calendar.getInstance();
把c1对象的日期加上10,也就是c1也就表示为10天后的日期,其它所有的数值会被重新计算
c1.add(Calendar.DATE, 10);
把c1对象的日期减去10,也就是c1也就表示为10天前的日期,其它所有的数值会被重新计算
c1.add(Calendar.DATE, -10);
其他字段属性的add的意义以此类推
Calendar类对象信息的获得
Calendar c1 = Calendar.getInstance(); // 获得年份 int year = c1.get(Calendar.YEAR); // 获得月份 int month = c1.get(Calendar.MONTH) + 1; // 获得日期 int date = c1.get(Calendar.DATE); // 获得小时 int hour = c1.get(Calendar.HOUR_OF_DAY); // 获得分钟 int minute = c1.get(Calendar.MINUTE); // 获得秒 int second = c1.get(Calendar.SECOND); // 获得星期几(注意(这个与Date类是不同的):1代表星期日、2代表星期1、3代表星期二,以此类推) int day = c1.get(Calendar.DAY_OF_WEEK);
这里主要是进行对API的回顾基本上不涉及什么具体的编程思想和面向对象的特殊思想。。。