자바스크립트가 비활성화 되어있습니다.
자바스크립트가 활성화 되어야 콘텐츠가 깨지지 않고 보이게 됩니다.
자바스크립트를 사용할수 있도록 옵션을 변경해 주세요.
- willbsoon

본문 바로가기
Java

java8 - ZonedDateTime 을 이용한 날짜 변환

by willbsoon 2020. 10. 19.

ZonedDateTime

ZonedDateTime 클래스는 타임존 또는 시차 개념이 필요한 날짜와 시간 정보를 나타내기 위해서 사용. public 생성자를 제공하지 않기 때문에 객체를 생성할 때는 now()나, of()와 같은 정적 메소드를 사용

ZonedDateTime nowSeoul = ZonedDateTime.now(ZoneId.of("Asia/Seoul"));
System.out.println("Now in Seoul is " + nowSeoul);

ZonedDateTime now = ZonedDateTime.now();
System.out.println("Now is " + now); // 시스템 zone id를 따라감

ZonedDateTime hanguelnal = ZonedDateTime.of(2020, 10, 9, 0, 0, 0, 0, ZoneId.of("Asia/Seoul"));
System.out.println("Hanguelnal is " + hanguelnal);

ZonedDateTime hanguelnal2 = Year.of(2020).atMonth(10).atDay(9).atTime(0, 0).atZone(ZoneId.of("Asia/Seoul"));
System.out.println("Hanguelnal is " + hanguelnal2);

 

ZonedDateTime = LocalDateTime + 타임존/시차

ZonedDateTime은 LocalDateTime에 타임존 또는 시차 개념이 추가되어 있음. 따라서 다음과 같이 ZonedDateTime은 LocalDateTime와 타임존이나 시차 개념을 더하거나 빼면서 상호 변환이 가능

LocalDate date = LocalDate.of(2020, 10, 9);
LocalTime time = LocalTime.of(0, 0);
LocalDateTime hanguelnal = LocalDateTime.of(date, time);
System.out.println("DateTime = " + hanguelnal);
System.out.println("Date = " + date);
System.out.println("Time = " + time);

// LocalDateTime to ZonedDateTime
ZonedDateTime zonedDateTime = ZonedDateTime.of(hanguelnal, ZoneId.of("Asia/Seoul"));
System.out.println("ZonedDateTime = " + zonedDateTime);
System.out.println("DateTime = " + zonedDateTime.toLocalDateTime());
System.out.println("Date = " + zonedDateTime.toLocalDate());
System.out.println("Time = " + zonedDateTime.toLocalTime());

 

 

ZoneId vs. ZoneOffset

ZoneId은 타임존, ZoneOffset은 시차. ZoneOffset는 UTC 기준으로 고정된 시간 차이를 양수나 음수로 나타내는 반면에 ZoneId는 이 시간 차이를 타임존 코드로 씀. 예를 들어 서울의 경우 타임존 코드는 Asia/Seoul이고 시차는 +0900

ZoneOffset seoulZoneOffset = ZoneOffset.of("+09:00");
System.out.println("+0900 Time = " + ZonedDateTime.now(seoulZoneOffset));
ZoneId seoulZoneId = ZoneId.of("Asia/Seoul");
System.out.println("Seoul Time = " + ZonedDateTime.now(seoulZoneId));

  Summer Time(일괄절약타임) -  여름에는 한 시간 더 일찍 시간이 가는 지역이 있음.

이런 도시를 대상으로 ZonedDateTime 객체를 만들 때는 ZoneId를 사용하는 편이 훨씬 유리함. 계절에 따라 변하는 시차를 알아서 처리해주기 때문.

 

 

다른 타임존/시차 적용

withZoneSameInstant() 메소드를 사용하면 ZonedDateTime에 다른 타임존이나 시차 적용가능. 아래는 2002년 월드컵 한국과 이탈리아 16강 경기의 서을 기준 시작 시간에 다른 도시의 타임존이나 다른 시차를 적용해봄

ZonedDateTime hanguelnal = Year.of(2020).atMonth(10).atDay(9).atTime(0, 0).atZone(ZoneId.of("Asia/Seoul"));
System.out.println("Hanguelnal =     " + hanguelnal);

ZonedDateTime hanguelnal_utc = hanguelnal.withZoneSameInstant(ZoneOffset.UTC);
ZonedDateTime hanguelnal_london = hanguelnal.withZoneSameInstant(ZoneId.of("Europe/London"));
ZonedDateTime hanguelnal_newYork = hanguelnal.withZoneSameInstant(ZoneOffset.of("-0400"));
ZonedDateTime hanguelnal_vancouver = hanguelnal.withZoneSameInstant(ZoneId.of("America/Vancouver"));

System.out.println("Hanguelnal_UTC =       " + hanguelnal_utc);
System.out.println("Hanguelnal_London =    " + hanguelnal_london);
System.out.println("Hanguelnal_NewYork =   " + hanguelnal_newYork);
System.out.println("Hanguelnal_Vancouver = " + hanguelnal_vancouver);

 

 

ZonedDateTime과 String 간 변환

ZonedDateTime의 format() 메소드에 DateTimeFormatter 객체를 넘기면 다양한 포멧의 문자열로 변환가능. DateTimeFormatter 클래스에서 정적 필드로 정의해 놓은 표준 포멧터, ofPattern(), ofLocalizedDateTime() 정적 메소드등을 사용해 변환 할 수 있음.

ZonedDateTime hanguelnal = Year.of(2020).atMonth(10).atDay(9).atTime(0, 0).atZone(ZoneId.of("Asia/Seoul"));

System.out.println(hanguelnal.format(DateTimeFormatter.ISO_DATE_TIME));
System.out.println(hanguelnal.format(DateTimeFormatter.ofPattern("yyyy/MM/dd/ HH:mm:ss z")));
System.out.println(hanguelnal.format(DateTimeFormatter.ofLocalizedDateTime(FormatStyle.FULL)));
System.out.println(hanguelnal.format(DateTimeFormatter.ofLocalizedDateTime(FormatStyle.FULL).withLocale(Locale.KOREA)));

반대로 문자열을 ZonedDateTime로 변환하기 위해서는 parse() 정적 메소드에 DateTimeFormatter 객체를 넘기면 됨.

아래는 모두 같은 케이스.

ZonedDateTime zdt1 = ZonedDateTime.parse("2020-10-09T00:00:00+09:00[Asia/Seoul]");
ZonedDateTime zdt2 = ZonedDateTime.parse("2020/10/09/ 00:00:00 KST", DateTimeFormatter.ofPattern("yyyy/MM/dd/ HH:mm:ss z"));
ZonedDateTime zdt3 = ZonedDateTime.parse("Friday, October 9, 2020 12:00:00 AM KST", DateTimeFormatter.ofLocalizedDateTime(FormatStyle.FULL));
ZonedDateTime zdt4 = ZonedDateTime.parse("2020년 10월 9일 금요일 오전 12시 00분 00초 KST", DateTimeFormatter.ofLocalizedDateTime(FormatStyle.FULL).withLocale(Locale.KOREA));

 

 

 

출처 : www.daleseo.com/java8-zoned-date-time/

댓글