[자바의정석]Chapter 10. 날짜와시간&형식화

seungwon·2023년 1월 16일
0

자바의 정석

목록 보기
10/14

1. 날짜와 시간

1.1 Calendar & Date

Date 클래스 -> Calendar 클래스 -> java.time 패키지

날짜와 시간을 다룰 목적으로 제공되어온 클래스(Date, Calendar)

👽 Calendar & GregorianCalendar

Calendar : 추상클래스, 직접 객체 생성 불가능,
메서드를 통해 완전히 구현된 클래스의 인스턴스를 얻어야 함 -> GregorianCalendar, BuddhistCalendar

-> getInstance() : 시스템의 국가와 지역설정을 확인해서 태국인 경우에 BuddhistCalendar의 인스턴스를 반환하고,그 외에는 GregorianCalendar의 인스턴스를 반환

👽 Date, Calendar 간의 변환

  • Calendar -> Date
  Calendar cal = Calendar.getlnstance();
  ...
  Date d = new Date (cal.getTimelnMillis()); // Date (long date)
  • Date -> Calendar
Date d = new Date();
...
Calendar cal = Calendar.getlnstance(); 
cal.setTime(d);

👽 Calendar 클래스의 데이터 가져오기

  • 인스턴스 생성 : getInstance()
    Calendar today = Calendar.getlnstance();
    • 기본적으로 현재 시스템의 날짜/시간에 대한 정보 가짐
    • 원하는 날짜나 시간으로 설정 : set()
       void set (int field, int value)
        void set(int year, int month, int date)
        void set(int year, int month, int date, int hourOfDay, int minute) 
        void set (int year, int month, int date, int hourOfDay, int minute, int 	second)
  • 원하는 필드의 값 얻어오기 : int get(int field)
    • field : Calendar에 정의된 static 상수
      • Calendar.YEAR
      • Calendar.MONTH : 월(0~11)
      • Calendar.WEEK_OF_YEAR : 이 달의 몇 째 주인지
      • Calendar.DATE
      • Calendar.HOUR : 0~11
      • Calendar.HOUR_OF_DAY : 0~23
        ...
  • 주요 메서드
    • boolean isLeapYear(int year) :매개변수 year가 윤년이면 true를 그렇지 않으면 false를 반환한다.
    • int dayDiff(int y1, int ml, int d1, int y2, int m2, int 62) : 두 날짜간의 차이를 일단위로 반환한다.
    • int getDayOfWeek (int year, int month, int day) : 지정한 날짜의 요일을 반환한다.(1~7, 1이 일요일)
    • String convertDayToDate (int day) : 일단위의 값을 년월일의 형태의 문자열로 변환하여 반환한다.
    • int convertDateToDay (int year, int month, int day) : 년월일을 입력받아서 일단위로 변환한다.

2. 형식화 클래스

java.text 패키지
숫자, 날짜, 텍스트 데이 터를 일정한 형식에 맞게 표현할 수 있는 방법

데이터 -> 형식화, 형식화된 데이터 -> 본래 데이터 둘 다 가능

2.1 DecimalFormat

  1. 출력형식의 패턴으로 DecimalFormat 인스턴스 생성
  2. 출력하고자 하는 문자열로 format() 호출
    double number = 1234567.89;
    DecimalFormat df = new DecimalFormat("#.#E0"); 
    String result = df.format(number);
  • 패턴에 사용되는 기호

2.2 SimpleDateFormat

날짜를 출력하는 방식

날짜 계산 : Date, Calendar

사용하는 방법

  • 출력형식의 패턴 작성 -> SimpleDateFormat 인스턴스 생성
  • 출력하고자 하는 Date 인스턴스로 format(Date d)를 호출

ex)

Date today = new Date();
SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dcT);

// 오늘 날짜를 yyyy-MM-dd형태로 변환하여 반환한다. 
String result = df.format(today);
  • SimpleDate Format의 parse(String source) : 문자열source -> 날짜Date인스턴스로 변환
import java.util.*;
import java.text.*;

class DateFormatEx3 {
	public static void main(String[] args) {
		DateFormat df = new SimpleDateFormat ("yyyy년 MM월 dd일"); 
        DateFormat df2 = new SimpleDateFormat("yyyy/MM/dd");
	try {
		Date d = df.parse ("2015년 11월 23일"); // ☑️
        System.out.println(df2.format(d);
	} catch(Exception e) {} } // main
}
  • 패턴 예시
    • SimpleDateFormat("yyyy-MM-dd");
    • SimpleDateFormat yy년 MMM dd일 E요일");
    • SimpleDateFormat("yyyy-MM-dd HH:mm:ss.SSS”;
    • SimpleDateFormat("yyyy-MM-dd hh:mm:ss a”);

2.3 ChoiceFormat

특정 범위에 속하는 값을 문자열로 변환

ex) 점수 -> 등급
60<=점수<7060<=점수<70 : D
70<=점수<8070<=점수<80 : C
80<=점수<9080<=점수<90 : B
90<=점수<10090<=점수<100 : A

import java.text.*;
class ChoiceFormatEx1 {
	public static void main (String[] args) {
		double [] limits = {60, 70, 80, 90); // 범위의 경계값 
		//1imits, grades간의 순서와 개수를 맞추어야 한다.
		String[l grades = ("D", "C", "B", "A"); // 치환할 문자열
		int [] scores = { 100, 95, 88, 70, 52, 60, 701;
		
		ChoiceFormat form = new ChoiceFormat (limits, grades); //☑️
		for (int i=0;i<scores.length;i++) {
        	System.out.printIn (scores [il+":"+form.format (scores [i]));
		}
	}
}
  • 범위의 경계값을 패턴으로 표시 - 구분자 : '#', '<'
    limit#value
    # : 경계값을 범위에 포함
    < : 범위에 포함x
    String pattern = "60#D|70#이 80<B|90#A"; 
    int[] scores = { 91, 90, 80, 88, 70, 52, 60};

    91 : A
    90 : A
    80 : C
    88 : B
    70 : C
    52 : D
    60 : D

2.4 MessageFormat

  • 데이터를 정해진 양식에 맞게 출력
  • 하나의 데이터를 다양한 양식으로 출력
  • 지정된 양식에서 필요한 데이터만 추출(== SimpleDateFormat의 parse)
  • 양식에 맞게 출력
import java.text.*
class MessageFormatEx2 {
	public static void main (String[] args) {
		String tableName = "CUST INFO";
		String msg = "INSERT. INTO "+ tableName+" VALUES (''(0)'', ''(1)'`, (2)``, ''(3)'');";
		Object [] [] arguments = {
			{"이자바", " 02-123-1234", "27", "07-09"), 
            {"김프로", " 032-333-1234", "33", "10-07"},
		}:
		for (int i=0; i < arguments.length; i++){
			String result = MessageFormat. format(msg, arguments[i]); //☑️
			System.out.printIn (result);
		}
	}
}
  • 데이터 추출

    import java.text.*;
    class MessageFormatEx3 {
        public static void main(String[] args) throws Exception {
          String[] data = {
          "INSERT INTO CUST_INFO VALUES ('이자바','02-123-1234', 27, '07-09');", 	
          "INSERT INTO CUST一INFO VALUES ('김프로','032-333-1234', 33, '10-07');"
    
          String pattern = "INSERT INTO CUST_INFO VALUES ({0},{1},{2},{3});"; 
          MessageFormat mf = new MessageFormat(pattern); // ☑️ 
    
          for(int i=0; i < data.length;i++) { 
              Object[] objs = mf.parse(data[i]); // ☑️ 
              for(int j=0; j < objs.length; j++) {
                  System.out.print(objs[j] +",");
              }
              System.out.println();
       }
    }
      import java.util.*; 
      import java.text.*; 
      import java.io.*;
      
      class MessageFormatEx4 {
      	public static void main(String[] args) throws Exception {
            String tableName = "CUST_INFO"; 
            String fileName = "data4.txt";
            String msg = "INSERT INTO "+ tableName+ ” VALUES ({0},{1},{2},{3});"; 
            Scanner s = new Scanner(new File(fileName));
            
            String pattern = "{0},{1},{2},{3}"; 
            MessageFormat mf = new MessageFormat(pattern); //☑️
            
            while(s.hasNextLine()) {
          	String line = s.nextLine();
              Object[] objs = mf.parse(line); //☑️
              
              System.out.println(MessageFormat.format(msg, objs));
    		    }
        }
      s.close();
    } // main
    

3. java.time 패키지

  • immutable
    • 날짜/시간을 변경하는 메서드들은 기존의 객체 변경x, 새로운 객체 반환
      -> 멀티쓰레드 환경에 안전

👽 날짜, 시간을 별도의 클래스로 분리

  • 날짜 : LocalDate 클래스
  • 시간 : LocalTime 클래스
  • 날짜 + 시간 : LocalDateTime 클래스
  • 시간대 + 날짜 + 시간 : ZonedDateTime 클래스
  • 날짜간의 차이 : Period 클래스
  • 시간 차이 : Duration 클래스
  • 날짜 계산들을 대신해 주는 메서드들 포함 : TemporalAdjusters 클래스

👽 객체 생성

now() : 현재 날짜, 시간
of() : 날짜/시간 지정

LocalDate date = LocalDate.nowf) ; // 2015-11-23
LocalTime time = LocalTime.now(); // 21:54:01.875 
LocalDateTime dateTime = LocalDateTime.now();//2015-11-23TI1:54:01.875 
ZonedDateTime dateTimelnKr = ZonedDateTime.now();
// 2015-ll-23T21:54:01.875+09:00[Asia/Seoul]

👽 관련 인터페이스(Temporal, TemporalAmount)

  • Temporal, TemporalAccessor, TemporalAdjuster를 구현한 클래스
    : LocalDate, LocalTime, LocalDateTime, ZonedDateTime, Instant 등
  • TemporalAmount를 구현한 클래스
    : Period, Duration
  • TemporalUnit(날짜와 시간의 필드 정의 - 년, 월, 일 등)
    : 열거형 ChronoUnit이 구현

👽 관련 메소드

  • get()/getXXX() : 날짜와 시간에서 특정 필드의 값만을 얻을 때
  • plus() 또는 minus() : 특정 날짜와 시간에서 지정된 단위의 값을 더하거나 뻘 때
    • 열거형 ChronoUnit을 함께 사용
  • 특정 필드 값 변경 : with(), plus(), minus()
  • 날짜/시간 비교 : isAfter(), isBefore(), isEqual()

👽 Instant

에포크 타임(EPOCH TIME, 1970-01-01 00:00:00 UTC)부터 경과된 시간 을 나노초 단위로 표현한 것

  • 단일 진법으로만 다루기 때문에 계산 하기 쉬움
  • 기존의 java.util.Date를 대체하기 위한 것
cf. 목차

3.2 LocalDate, LocalTime
3.3 Instant
3.4 LocalDateTime, ZonedDateTime
3.5 TemporalAdiusters
3.6 Period와 Duration
3.7 파싱과 포맷

0개의 댓글