java8時間API介紹及使用
java7及之前版本,推薦使用jodatime
java8提供的datetime api參考了jodatime
在新的時間API中,
Instant
表示一個精確的時間點,
Duration
和Period
表示兩個時間點之間的時間量。 LocalDate
表示日期,即xx年xx月xx日,
即不包括時間也不帶時區。LocalTime
與LocalDate
類似。
LocalDateTime
則包含日期和時間。
OffsetDateTime表示一個帶ZoneOffset的時間。
ZoneDateTime
表示一個帶時區的時間。 DateTimeFormatter
提供格式化和解析功能。
java8的時間api解析網上很多,不詳細展開了。
下圖來自百度:
由於項目需要,需要將時間全部改造為GMT格式,即帶時區的時間格式
不同時區的同一時刻的時間戳都是一樣的,即時間戳都是不同時區相對於1970年的間隔絕對值,2016-10-10T20:00:00.000+1:00與2016-10-10T23:00:00.000+4:00的時間戳一樣,表示同一時刻。所以講string類型的時間字符串轉換long型再格式化成不同時區的時間。
以下工具類僅為參考:
public class OffsetDateTimeTool { //private static final ZoneOffset OFFSET_ID = ZoneOffset.of("+08:00"); private static final ZoneOffset OFFSET_ID = getOFFSET_ID(); /** * String 轉 OffsetDateTime */ public static String getZoneStringDateTime(CharSequence text){ return formatDateTime(OffsetDateTime.of(LocalDateTimeTool.parseTime(text.toString()),OFFSET_ID) ,TimeFormat.LONG_DATE_PATTERN_WITH_TIME_ZONE.value()); } /** * String 轉 OffsetDateTime 轉 long 轉 OffsetDateTime 格式化 String */ public static String getStringDateTime(CharSequence text) { return formatDateTime(OffsetDateTime.ofInstant(Instant.ofEpochMilli(getLongDateTime(text ,TimeFormat.LONG_DATE_PATTERN_WITH_TIME_ZONE.value(),getOffset(text.toString()))),OFFSET_ID) ,TimeFormat.LONG_DATE_PATTERN_LINE.value()); } /** * String 轉 OffsetDateTime 轉 long */ public static long getLongDateTime(CharSequence text, String patten, String offsetId) { return getLong(parse(text,patten,offsetId))*1000; } /** * OffsetDateTime 轉 long */ public static long getLong(OffsetDateTime offsetDateTime) { return offsetDateTime.getLong(ChronoField.INSTANT_SECONDS); } /** * 根據字符串設置日期 * * @return OffsetDateTime */ public static OffsetDateTime parse(CharSequence text, String patten, String offsetId) { LocalDateTime localDateTime = LocalDateTime.parse(text, DateTimeFormatter.ofPattern(patten)); return OffsetDateTime.of(localDateTime, ZoneOffset.of(offsetId)); } /** * 格式化時間 */ public static String formatDateTime(OffsetDateTime dateTime, String patten) { return dateTime.format(DateTimeFormatter.ofPattern(patten)); } /** * 獲取系統時區 */ public static ZoneOffset getOFFSET_ID(){ return LocalDateTime.now(ZoneOffset.systemDefault()).atZone(ZoneOffset.systemDefault()).getOffset(); } /** * 獲取string時區 */ public static String getOffset(String date){ return date.substring(date.length()-6,date.length()); } /** * 獲取當前時間 在ISO-8601日歷系統中的UTC /格林威治偏移的日期時間,如2017-12-03T10:15:30+08:00 */ public static OffsetDateTime getDateTimeNow() { return OffsetDateTime.now(); } /** * 獲取時間(只設置年月日) */ public static OffsetDateTime getDateTime(int year, int month, int day , String offsetId) { return getDateTime(year, month, day, 0, 0, 0, 0 , ZoneOffset.of(offsetId)); } /** * 獲取時間 * * @param year * 年 * @param month * 月 * @param day * 日 * @param hour * 時 * @param minute * 分 * @param second * 秒 * @param nanoOfSecond * 納秒 * @param zoneOffset * 時區 * @return OffsetDateTime */ public static OffsetDateTime getDateTime(int year, int month, int day, int hour, int minute, int second, int nanoOfSecond, ZoneOffset zoneOffset) { return OffsetDateTime.of(year, month, day, hour, minute, second, nanoOfSecond, zoneOffset); } /** * 內部枚舉類 */ public enum TimeFormat { //短時間格式 年月日 /** *時間格式:yyyy-MM-dd HH:mm:ss */ LONG_DATE_PATTERN_LINE("yyyy-MM-dd HH:mm:ss"), LONG_DATE_PATTERN_WITH_TIME_ZONE("yyyy-MM-dd'T'HH:mm:ss.SSSXXX"); private String value = ""; TimeFormat(String value) { this.value = value; } public String value() { return this.value; } } public static void main(String args[]) { System.out.println("getLongDateTime : " + getLongDateTime("2018-06-05T08:00:00.000+08:00" ,TimeFormat.LONG_DATE_PATTERN_WITH_TIME_ZONE.value(),getOffset("2018-06-05T04:00:00.000+08:00") )); System.out.println("getLongDateTime : " + getLongDateTime("2018-06-05T04:00:00.000+04:00" ,TimeFormat.LONG_DATE_PATTERN_WITH_TIME_ZONE.value(),getOffset("2018-06-05T04:00:00.000+04:00") )); System.out.println("getStringDateTime :" + getStringDateTime("2018-06-05T04:00:00.000-12:00")); System.out.println("getZoneStringDateTime:" + getZoneStringDateTime("2018-06-05 04:00:00")); } }