緒論
我們相信大多數(shù)有經(jīng)驗(yàn)的程序員都會贊同java8之前的庫對日期和時間的支持非常的不理想闷盔。然而,java8引入了全新的日期和時間API就是要解決這個問題。
LocalDate,LocalTime,Instant,Duration以及Period
使用LocalDate和LocalTime
LocalDate
LocalDate的實(shí)例是一個不可變的對象,它只提供了簡單的日期,并不含當(dāng)天的時間信息科贬。另外,它也不附帶任何與市區(qū)相關(guān)的信息鳖悠。
你可以通過靜態(tài)工廠方法of創(chuàng)建一個LocalDate實(shí)例榜掌。LocalDate實(shí)例提供了多種方法來讀取常用的值,比如年份乘综,月份憎账,星期幾。
LocalDate date = LocalDate.of(2017,6,23);
int year = date.getYear();//2017
Month month = date.getMonth();//6
int day = date.getDayOfMonth; //23
DayOfWeek dow = date.getDayOfWeek();//Fridiay
int len = date.lenghtofMonth();//30
boolean leap = date.isLwapYear();//false
你還可以使用工廠方法從系統(tǒng)時鐘中獲取當(dāng)前的日期
LocalDate today = LocalDate.now();
LocalTime
LocalTime time = LocalTime.of(13,45,20);
int hour = time.getHour(); //13
int minute = time.getHour(); // 45
int second = time.getMinute();// 20
LocalDate和LocalTime都可以通過解析代表他們的字符串創(chuàng)建卡辰。使用靜態(tài)方法parse胞皱,可以實(shí)現(xiàn)這一目的:
LocalDate date = LocalDate.parse("2017-03-18");
LocalTime time = LocalTime.parse("13:45:20");
你可以向parse方法傳遞一個DateTimeFormatter.該類的實(shí)例定義了如何格式化一個日期或者時間對象。正如我們之前所介紹的九妈,他是替換老版java.util.DateFormat的推薦替代品反砌。同時,也請注意萌朱,一旦傳遞的字符串參數(shù)無法被解析為合法的LocalDate和LocalTime對象宴树,這兩個parse方法都會跑出一個繼承自RuntimeException的DateTimeParseException異常。
合并日期和時間
這個復(fù)合類叫做LocalDateTime,是LocalDate和LocalTime的合體晶疼。它同時表示了日期和時間酒贬,但不帶有時區(qū)信息又憨,你可以直接創(chuàng)建,也可以通過合并日期和時間對象構(gòu)造锭吨。
LocalDateTime dt1 = LcoalDateTime.of(2017,3,18,13,45,20);
LocalDateTime dt2 = LocalDateTime.of(date,time);
LocalDateTime dt3 = date.atTime(13,45,20);
LocalDateTime dt4 = date.atTime(time);
LocalDateTime dt5 = time.atDate(date);
注意竟块,通過他們各自的atTime或者atDate方法,向LocalDate傳遞了一個時間對象耐齐,或者向LoaclTime傳遞一個日期對象的方式,你可以創(chuàng)建一個LocalDateTime對象蒋情。你也可以使用toLocalDate或者toLocalTime方法埠况,從LocalDateTime中提起LocalDate或者LocalTime組件:
LocalDate date1 = dt1.toLocalDate();
LocalDate time1 = dt1.toLocalTime();
定義Duration或者Period
我們已經(jīng)了解了創(chuàng)建Temporal實(shí)例的幾種方法。很自然地你會想到棵癣,我們需要創(chuàng)建兩個Temporal對象之間的duration辕翰。Duration類的靜態(tài)工廠方法between就是為這個目的而設(shè)計的。你可以創(chuàng)建兩個LocalTime對象狈谊,兩個LocalDateTimes對象喜命。或者兩個Instant對象之間的duration河劝。
Duration d1 = Duration.between(time1,time2);
Duration d1 = Duration.between(dateTime1,dateTime2);
Duration d2 = Duration.between(instant1,instant2);
由于LocalDateTime和Instant是為了不同的目的而設(shè)計的壁榕,一個是為了便于人閱讀使用,另一個是為了便于機(jī)器處理赎瞎,所以你不能將二者混用牌里。此外,由于Duration主要用于以秒和納秒衡量時間的長短务甥,你不能僅僅向between方法傳遞一個LcoalDate對象做參數(shù)牡辽。
如果你需要以年,月敞临,或者日的方式對多個時間單位建模态辛,可以使用Period類。使用該類的工廠方法between,你可以使用得到兩個LocalDate之間的時長挺尿。
Period tenDays = Period.between((LocalDate.of(2017,3,8),LocalDate.of(2017.3.18));
操縱奏黑,解析和格式化日期
如果你已經(jīng)有一個LocalDate對象,想要創(chuàng)建它的一個修改版票髓,最直接也是最簡單的方法是使用withAttribute方法攀涵。
LocalDate date1 = LcoalDate.of(2014.3.18);//2014-03-18
LocalDate date2 = date1.withYear(2011);//2011-03-18
LocalDate date3 = date2.withDayOfMonth(25);//2011-03-25
LocalDate date4 = date3.with(ChronoField.MONTH_OF_YEAR,9);//2011-09-25
以相對方式修改LocalDate對象的屬性
LocalDate date1 = LocalDate.of(2014,3,18);
LocalDate date2 = date1.plusWeeks(1);//2014-03-25
LocalDate date3 = date2.minusYears(3);//2011-03-25
使用TemporalAdjuster
截止目前,你所看到的所有日期操作都是相對比較直接的洽沟。有的時候以故,你需要進(jìn)行更加復(fù)雜的操作,比如裆操,將日期調(diào)整到下個周日怒详,下個工作日炉媒,或者是本月的最后一天。這時昆烁,你可以使用重載版本的with方法吊骤,向其傳遞一個提供了更多定制化選擇的TemporalAdjuster對象,更加靈活地處理日期静尼。
LocalDate date1 = LocalDate.of(2014,3,18);//2014-03-18
LocalDate date2 = date1.with(nextOrSame(DayOfWeek.SUNDAY));//2014-03-23
LocalDate date3 = date2.with(lastDayOfMonth());//2014-03-31
TemporalAdjuster中包含的工廠方法列表
打印輸出及解析日期-時間對象
LocalDate date = LocalDate.of(2014,3,18);
String s1 = date.format(DateTimeFormatter.BASIC_ISO_DATE);//20140318
String s2 = date.format(DateTimeFormatter.ISO_LOCAL_DATE);//2014-03-18
你也可以通過解析代表日期或時間的字符串重新創(chuàng)建該日期對象白粉。所有的日期和時間API都提供了表示時間點(diǎn)或者時間段的工廠方法,你可以使用工廠方法parse達(dá)到重新創(chuàng)建該日期對象的目的:
LocalDate date1 = LocalDate.parse("20140318",DateTimeFormatter.BASIC_ISO_DATE);
lcoalDate date2 = LocalDate.parse("2014-03-18",DateTimeFormatter.ISO_LOCAL_DATE);
和老的java.util.DateFormat相比較鼠渺,所有的DateTimeFormatter實(shí)例都是線程安全的鸭巴。所以,你能夠以單例模式創(chuàng)建格式器實(shí)例拦盹,就像DateTimeFomatter所定義的那些常量鹃祖,并能在多個線程間共享這些實(shí)例。DateTimeFormatter類還支持一個靜態(tài)工廠方法普舆,它可以按照某個特定的模式創(chuàng)建格式器恬口。
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("dd/MM/yyyy");
LocalDate date1 = LocalDate.of(2014,3,18);
String fomattedDate = date1.format(formatter);
LocalDate date 2 = LocalDate.parse(formattedDate,formatter);