-
Bug
-
Resolution: Duplicate
-
P4
-
None
-
8u40
-
x86
-
windows_8
FULL PRODUCT VERSION :
java version "1.8.0_40"
Java(TM) SE Runtime Environment (build 1.8.0_40-b26)
Java HotSpot(TM) 64-Bit Server VM (build 25.40-b25, mixed mode)
ADDITIONAL OS VERSION INFORMATION :
Microsoft Windows [Version 6.3.9600]
A DESCRIPTION OF THE PROBLEM :
As the Javadoc says: "GregorianCalendar is a hybrid calendar that supports both the Julian and Gregorian calendar systems"
So I wrote a method to convert dates from the Julian calendar system to the Gregorian calendar system by using GregorianCalendar. This method works correctly for all dates, starting from 1899-12-21. However, dates before 1899-12-21 are off by one day.
STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
Run the test case. In the actual result, you can see that there is a gap: there is no date in the Julian calendar system that maps to 1900-01-01. This causes all dates before the Julian date 1899-12-21 to be off by one day. Another illustration of this, is the fact that 0200-03-01 is mapped to 0200-02-28, though it should be mapped to 0200-03-01.
EXPECTED VERSUS ACTUAL BEHAVIOR :
EXPECTED -
0200-03-01 maps to 0200-03-01
1899-12-20 maps to 1900-01-01
1899-12-21 maps to 1900-01-02
ACTUAL -
0200-03-01 maps to 0200-02-28
1899-12-20 maps to 1899-12-31
1899-12-21 maps to 1900-01-02
REPRODUCIBILITY :
This bug can be reproduced always.
---------- BEGIN SOURCE ----------
import java.time.LocalDate;
import java.time.Month;
import java.util.Calendar;
import java.util.Date;
import java.util.GregorianCalendar;
public class JulianBug {
public static void main(String[] args) {
System.out.println(ofJulian(200, Month.MARCH, 1) + " must be 0200-03-01");
System.out.println(ofJulian(1899, Month.DECEMBER, 20) + " must be 1900-01-01");
System.out.println(ofJulian(1899, Month.DECEMBER, 21) + " must be 1900-01-02");
}
public static LocalDate ofJulian(int year, Month month, int dayOfMonth) {
GregorianCalendar julianCalendar = new GregorianCalendar();
julianCalendar.setGregorianChange(new Date(Long.MAX_VALUE));
julianCalendar.clear();
julianCalendar.set(Calendar.ERA, GregorianCalendar.AD);
julianCalendar.set(year, month.getValue() - 1, dayOfMonth);
return julianCalendar.toZonedDateTime().toLocalDate();
}
}
---------- END SOURCE ----------
java version "1.8.0_40"
Java(TM) SE Runtime Environment (build 1.8.0_40-b26)
Java HotSpot(TM) 64-Bit Server VM (build 25.40-b25, mixed mode)
ADDITIONAL OS VERSION INFORMATION :
Microsoft Windows [Version 6.3.9600]
A DESCRIPTION OF THE PROBLEM :
As the Javadoc says: "GregorianCalendar is a hybrid calendar that supports both the Julian and Gregorian calendar systems"
So I wrote a method to convert dates from the Julian calendar system to the Gregorian calendar system by using GregorianCalendar. This method works correctly for all dates, starting from 1899-12-21. However, dates before 1899-12-21 are off by one day.
STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
Run the test case. In the actual result, you can see that there is a gap: there is no date in the Julian calendar system that maps to 1900-01-01. This causes all dates before the Julian date 1899-12-21 to be off by one day. Another illustration of this, is the fact that 0200-03-01 is mapped to 0200-02-28, though it should be mapped to 0200-03-01.
EXPECTED VERSUS ACTUAL BEHAVIOR :
EXPECTED -
0200-03-01 maps to 0200-03-01
1899-12-20 maps to 1900-01-01
1899-12-21 maps to 1900-01-02
ACTUAL -
0200-03-01 maps to 0200-02-28
1899-12-20 maps to 1899-12-31
1899-12-21 maps to 1900-01-02
REPRODUCIBILITY :
This bug can be reproduced always.
---------- BEGIN SOURCE ----------
import java.time.LocalDate;
import java.time.Month;
import java.util.Calendar;
import java.util.Date;
import java.util.GregorianCalendar;
public class JulianBug {
public static void main(String[] args) {
System.out.println(ofJulian(200, Month.MARCH, 1) + " must be 0200-03-01");
System.out.println(ofJulian(1899, Month.DECEMBER, 20) + " must be 1900-01-01");
System.out.println(ofJulian(1899, Month.DECEMBER, 21) + " must be 1900-01-02");
}
public static LocalDate ofJulian(int year, Month month, int dayOfMonth) {
GregorianCalendar julianCalendar = new GregorianCalendar();
julianCalendar.setGregorianChange(new Date(Long.MAX_VALUE));
julianCalendar.clear();
julianCalendar.set(Calendar.ERA, GregorianCalendar.AD);
julianCalendar.set(year, month.getValue() - 1, dayOfMonth);
return julianCalendar.toZonedDateTime().toLocalDate();
}
}
---------- END SOURCE ----------
- duplicates
-
JDK-6281408 (tz) TimeZone doesn't support Local Mean Time correctly
- Closed