Date
은 JDK
1.0부터, Calendar
는 JDK
1.1부터 지원된 클래스로, 오래된만큼 기능적으로 빈약하고 단점이 많음.
그래서 JDK
1.8부터는 java.time
패키지가 나와서 많은 부분을 개선함.
레거시 이해 차원에서 Date
와 Calendar
클래스를 알고는 있어야함.
Calendar
는 추상클래스이므로 인스턴스 직접 생성 불가.
getInstance()
메서드를 활용하면 Calendar
를 상속받아 구현한 GregorianCalendar
클래스의 인스턴스를 얻을 수 있음
Calendar c = new Calendar(); // (X)
Calendar c = Calendar.getInstance(); // (O)
Calendar
가 생기면서 Date
는 deprecated.
그럼에도 Date
를 필요로 하는 메서드가 있어서 변환법은 알아두어야함.
Calendar → Date
Calendar c = Calendar.getInstance();
Date d = new Date(cal.getTimeInMillis());
Date → Calendar
Date d = new Date();
Calendar c = Calendar.getInstance();
cal.setTime(d);
Calendar.getInstance()
는 기본적으로 현재 시스템의 날짜와 시간 정보를 갖고 있음.
여기서 정보를 추출하려면 get
메서드를, 다른 날짜나 시간으로 설정하려면 set
메서드를 활용
int get
(int field)
매개변수 field에는 Calendar
에 정의된 static
상수들이 들어감.
Calendar cal = Calendar.getInstance();
cal.get(Calendar.DATE); // 26 (일)
cal.get(Calendar.HOUR); // 1 (시)
📌 [주의]
Calendar.MONTH
값의 범위는 0 ~ 11 이므로, 실제 월은 여기에 1을 더해서 얻을 수 있음
Calendar.DAY_OF_WEEK
값은 요일을 나타내는 숫자로, 일요일(0)부터 시작
void set
(int field, int value)
매개변수 field에는 Calendar
에 정의된 static
상수들이 들어가고, value에는 field를 대체할 값이 들어감.
다음과 같이 여러 값을 한번에 지정하여 바꾸는 것도 가능하게끔 오버로드 되어있음
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)
Calendar cal = Calendar.getInstance();
cal.set(Calendar.DATE, 7); // 날짜(일)을 7로 바꿈
cal.set(2077, 6, 7); // 날짜(연, 월, 일)을 2077년 7월 7일로 바꿈
두 날짜 간의 차이를 구하려면 둘 다 초단위로 환산한 뒤에 차이를 구하면 됨.
getTimeInMillis()
가 1/1000초 단위로 변환시켜주므로, 이 값을 1000으로 나누면 초 단위 값이 됨.
두 날짜 간의 단순 전후관계를 알기 위해서는 차이를 구해 양수인지 음수인지 보거나,
boolean before
(Object when)
boolean after
(Object when)
둘 중 하나의 메서드를 통해서도 알 수 있음
활용 예시) 태어난 날짜와 오늘 날짜의 차이 구하기
class CalendarExample {
public static void main(String[] args) {
final int[] TIME_DIVISOR = {31536000, 86400, 3600, 60, 1};
final String[] TIME_UNIT = {"년 ", "일 " ,"시간 ", "분 ", "초"};
Calendar birthDate = Calendar.getInstance();
birthDate.set(1996, Calendar.OCTOBER, 28, 16, 0, 0);
Calendar today = Calendar.getInstance();
long difference = (today.getTimeInMillis() - birthDate.getTimeInMillis()) / 1000;
System.out.printf("태어난 지 %d초가 지났습니다.%n", difference);
StringBuffer fStringInTimeUnit = new StringBuffer("");
for (int i = 0; i < TIME_DIVISOR.length; i++) {
fStringInTimeUnit.append(difference / TIME_DIVISOR[i]).append(TIME_UNIT[i]);
difference %= TIME_DIVISOR[i];
}
System.out.printf("태어난 지 %s가 지났습니다.", fStringInTimeUnit);
}
}
add
(int field, int amount) 메서드를 사용하면 지정한 field를 amount 만큼 증감할 수 있음
roll
(int field, int amount) 메서드도 같은 기능이지만, 증감 결과로 다른 field에 영향을 주지 않는다는 점이 다름
Calendar date = Calendar.getInstance();
date.set(Calendar.DATE, 27); // 날짜(일)을 27일로 지정함
date.add(Calendar.DATE, 10); // 날짜(일)에 10을 더함 (월이 넘어가면서 자동적으로 MONTH도 +1 됨)
date.add(Calendar.DATE, 10); // 날짜(일)에 10을 더함 (MONTH에 영향을 주지 않음)
📌 [주의] 날짜(일)을 31일로 지정한 상태에서 월을 31보다 적은 날을 가진 것으로 바꾸면, 일도 그에 맞는 값으로 바뀜
ex) 1월 31일 → 2월로 변경 → 2월 28일