2

I use class Calendar to create Date. But in my test case when i set date is 31/12 or 30/12, year of my date is my set year of date + 1. Example 2018-12-29 -> 2018-12-29 but 2018-12-30 -> 2019-12-30. I don't know why ? My code:

import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;

public class MyClass {
    public static void main(String args[]) {
        calendarBug(2018, 11, 29);
        calendarBug(2018, 11, 30);
    }

    public static void calendarBug(int year, int month, int day) {
        Calendar calendar = Calendar.getInstance();
        calendar.set(Calendar.YEAR, year);
        calendar.set(Calendar.MONTH, month);
        calendar.set(Calendar.DAY_OF_MONTH, day);
        Date date = calendar.getTime();
        System.out.println(new SimpleDateFormat("YYYY-MM-dd").format(date));
    }
}

Output:

2018-12-29
2019-12-30
Ole V.V.
  • 81,772
  • 15
  • 137
  • 161
Minh Nguyen
  • 363
  • 3
  • 13
  • What happens when you use: `calendar.set(year, month, day);` ? – Chris623 Mar 11 '19 at 07:55
  • 2
    If not using java8 or greater use https://www.threeten.org/threetenbp/ – Scary Wombat Mar 11 '19 at 08:01
  • And/or set your output format to "YYYY-MM-dd HH:mm:ssZ" – Joakim Danielson Mar 11 '19 at 08:03
  • @Chris623 no one change. – Minh Nguyen Mar 11 '19 at 08:04
  • @ScaryWombat i try it but this code with `calendarBug(2018, 11, 31)` output is 2019-12-31 – Minh Nguyen Mar 11 '19 at 08:06
  • For reference, I was able to reproduce this using `calendar.setTimeZone(TimeZone.getTimeZone("GMT-12"));` – Joakim Danielson Mar 11 '19 at 08:17
  • 1
    I recommend you don’t use `SimpleDateFormat`, `Calendar` and `Date`. Those classes are poorly designed and long outdated, the first in particular notoriously troublesome. Instead use `LocalDate` from [java.time, the modern Java date and time API](https://docs.oracle.com/javase/tutorial/datetime/). – Ole V.V. Mar 12 '19 at 00:09
  • Wrong data type. For a date-only value, use [`LocalDate`](https://docs.oracle.com/en/java/javase/11/docs/api/java.base/java/time/LocalDate.html), not `Calendar`. Despite the names, both `Date` & `Calendar` represent moments rather than dates. – Basil Bourque Mar 12 '19 at 01:48

1 Answers1

11

YYYY represents for week year. Use yyyy instead.

From javadocs:

A week year is in sync with a WEEK_OF_YEAR cycle. All weeks between the first and last weeks (inclusive) have the same week year value. Therefore, the first and last days of a week year may have different calendar year values.

For example, January 1, 1998 is a Thursday. If getFirstDayOfWeek() is MONDAY and getMinimalDaysInFirstWeek() is 4 (ISO 8601 standard compatible setting), then week 1 of 1998 starts on December 29, 1997, and ends on January 4, 1998. The week year is 1998 for the last three days of calendar year 1997. If, however, getFirstDayOfWeek() is SUNDAY, then week 1 of 1998 starts on January 4, 1998, and ends on January 10, 1998; the first three days of 1998 then are part of week 53 of 1997 and their week year is 1997.

Cà phê đen
  • 1,883
  • 2
  • 21
  • 20