import tauzaman.field.*; import tauzaman.timestamp.*; import tauzaman.calendar.*; import tauzaman.calendar.Calendar; import tauzaman.calendricsystem.*; import tauzaman.TauZamanException; /* * This class implements all the methods necessary for a simple Gregorian Calendar * that will work with tauZaman. Here are the following assumptions I made while * writing this calendar: * # It starts on January 1, 0001 AD and goes forward. * # There is no support for negative granules (ones before January 1, 0001 00:00:00 * at this time). * # There are no prophetic calculations that occur (i.e. estimating Gregorian * Calendar information before AD). * # Each granule starts at 1 (not 0), therefore, I am doing 1-based counting * of the granules. Therefore, second 1 = January 1, 0001 00:00:00. * # Leap years and seconds have be implemented according to the Gregorian * Calendar rules for leap years/seconds. * * Last Updated: 2003/3/16 by Jessica Miller */ public class ADGregorianCalendar { /******************************************************************************/ /* Constants */ /******************************************************************************/ private static final long NUM_YEARS_LEAP_CYCLE = 4; private static final long NUM_YEARS_CENTURY = 100; private static final long NUM_YEARS_GC_CYCLE = 400; private static final long NUM_MONTHS_YEAR = 12; private static final long NUM_MONTHS_LEAP_CYCLE = NUM_MONTHS_YEAR * NUM_YEARS_LEAP_CYCLE; private static final long NUM_MONTHS_CENTURY = NUM_MONTHS_YEAR * NUM_YEARS_CENTURY; private static final long NUM_MONTHS_GC_CYCLE = NUM_MONTHS_YEAR * NUM_YEARS_GC_CYCLE; private static final long NUM_DAYS_YEAR = 365; private static final long NUM_DAYS_LEAP_YEAR = 366; private static final long NUM_DAYS_LEAP_CYCLE = NUM_DAYS_YEAR * NUM_YEARS_LEAP_CYCLE + 1; private static final long NUM_DAYS_CENTURY = NUM_DAYS_YEAR * NUM_YEARS_CENTURY + (NUM_YEARS_CENTURY / NUM_YEARS_LEAP_CYCLE) - 1; private static final long NUM_DAYS_GC_CYCLE = NUM_DAYS_CENTURY * 4 + 1; private static final long NUM_HOURS_DAY = 24; private static final long NUM_HOURS_LEAP_YEAR = NUM_HOURS_DAY * NUM_DAYS_LEAP_YEAR; private static final long NUM_HOURS_YEAR = NUM_HOURS_DAY * NUM_DAYS_YEAR; private static final long NUM_HOURS_LEAP_CYCLE = NUM_HOURS_DAY * NUM_DAYS_LEAP_CYCLE; private static final long NUM_HOURS_CENTURY = NUM_HOURS_DAY * NUM_DAYS_CENTURY; private static final long NUM_HOURS_GC_CYCLE = NUM_HOURS_DAY * NUM_DAYS_GC_CYCLE; private static final long NUM_MINS_HOUR = 60; private static final long NUM_MINS_DAY = NUM_MINS_HOUR * 24; private static final long NUM_MINS_LEAP_YEAR = NUM_MINS_DAY * NUM_DAYS_LEAP_YEAR; private static final long NUM_MINS_YEAR = NUM_MINS_DAY * NUM_DAYS_YEAR; private static final long NUM_MINS_LEAP_CYCLE = NUM_MINS_DAY * NUM_DAYS_LEAP_CYCLE; private static final long NUM_MINS_CENTURY = NUM_MINS_DAY * NUM_DAYS_CENTURY; private static final long NUM_MINS_GC_CYCLE = NUM_MINS_DAY * NUM_DAYS_GC_CYCLE; private static final long NUM_SECS_MINUTE = 60; private static final long NUM_SECS_HOUR = NUM_SECS_MINUTE * 60; private static final long NUM_SECS_DAY = NUM_SECS_MINUTE * NUM_MINS_DAY; private static final long NUM_SECS_LEAP_YEAR = NUM_SECS_MINUTE * NUM_MINS_LEAP_YEAR; private static final long NUM_SECS_YEAR = NUM_SECS_MINUTE * NUM_MINS_YEAR; private static final long NUM_SECS_LEAP_CYCLE = NUM_SECS_MINUTE * NUM_MINS_LEAP_CYCLE; private static final long NUM_SECS_CENTURY = NUM_SECS_MINUTE * NUM_MINS_CENTURY; private static final long NUM_SECS_GC_CYCLE = NUM_SECS_MINUTE * NUM_MINS_GC_CYCLE; private static final int NON_LEAP_YEAR = 0; private static final int LEAP_YEAR = 1; private static final long[][] DAYS_IN_MONTHS = { { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31}, { 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31} }; private static final long[][] DAYS_COMPLETED_BY_MONTH = { { 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334, 365}, { 0, 31, 60, 91, 121, 152, 182, 213, 244, 274, 305, 335, 366} }; private static final long[] MINUTES_WITH_LEAP_SECONDS = { sumMinutes(1972, 06, 30, 23, 59), sumMinutes(1972, 12, 31, 23, 59), sumMinutes(1973, 12, 31, 23, 59), sumMinutes(1974, 12, 31, 23, 59), sumMinutes(1975, 12, 31, 23, 59), sumMinutes(1976, 12, 31, 23, 59), sumMinutes(1977, 12, 31, 23, 59), sumMinutes(1978, 12, 31, 23, 59), sumMinutes(1979, 12, 31, 23, 59), sumMinutes(1981, 06, 30, 23, 59), sumMinutes(1982, 06, 30, 23, 59), sumMinutes(1983, 06, 30, 23, 59), sumMinutes(1985, 06, 30, 23, 59), sumMinutes(1987, 12, 31, 23, 59), sumMinutes(1989, 12, 31, 23, 59), sumMinutes(1990, 12, 31, 23, 59), sumMinutes(1992, 06, 30, 23, 59), sumMinutes(1993, 06, 30, 23, 59), sumMinutes(1994, 06, 30, 23, 59), sumMinutes(1995, 12, 31, 23, 59), sumMinutes(1997, 06, 30, 23, 59), sumMinutes(1998, 12, 31, 23, 59) }; private static final long[] LEAP_SECONDS = { sumSeconds(1972, 06, 30, 23, 59, 60), sumSeconds(1972, 12, 31, 23, 59, 60), sumSeconds(1973, 12, 31, 23, 59, 60), sumSeconds(1974, 12, 31, 23, 59, 60), sumSeconds(1975, 12, 31, 23, 59, 60), sumSeconds(1976, 12, 31, 23, 59, 60), sumSeconds(1977, 12, 31, 23, 59, 60), sumSeconds(1978, 12, 31, 23, 59, 60), sumSeconds(1979, 12, 31, 23, 59, 60), sumSeconds(1981, 06, 30, 23, 59, 60), sumSeconds(1982, 06, 30, 23, 59, 60), sumSeconds(1983, 06, 30, 23, 59, 60), sumSeconds(1985, 06, 30, 23, 59, 60), sumSeconds(1987, 12, 31, 23, 59, 60), sumSeconds(1989, 12, 31, 23, 59, 60), sumSeconds(1990, 12, 31, 23, 59, 60), sumSeconds(1992, 06, 30, 23, 59, 60), sumSeconds(1993, 06, 30, 23, 59, 60), sumSeconds(1994, 06, 30, 23, 59, 60), sumSeconds(1995, 12, 31, 23, 59, 60), sumSeconds(1997, 06, 30, 23, 59, 60), sumSeconds(1998, 12, 31, 23, 59, 60) }; // Need these offsets because there is no 0th day, week, month or year of // this calendar's starting point public static final int SECOND_OFFSET = 1; public static final int MINUTE_OFFSET = 1; public static final int DAY_OFFSET = 1; public static final int WEEK_OFFSET = 1; public static final int MONTH_OFFSET = 1; public static final int YEAR_OFFSET = 1; // Constants for indices of array that is given back in the split public static final int YEAR_INDEX = 0; public static final int MONTH_INDEX = 1; public static final int DAY_INDEX = 2; public static final int HOUR_INDEX = 3; public static final int MINUTE_INDEX = 4; public static final int SECOND_INDEX = 5; public static final int SPLIT_ARRAY_SIZE = 6; /***************************************************************************/ /* Helper methods */ /***************************************************************************/ /* * Returns the number of leap seconds that have occurred up to (not * including) the given minute (away from January 1, 0001 00:00). * * @param minute minute from January 1, 0001 00:00 * @return number of leap seconds that have occurred since minute */ private static long getNumLeapSecsFromMin(long minute) { int i = 0; long numLeapSeconds = 0; while (i < MINUTES_WITH_LEAP_SECONDS.length && MINUTES_WITH_LEAP_SECONDS[i++] < minute) numLeapSeconds++; return numLeapSeconds; } /* * Returns the number of leap seconds that have occurred up to (and * including) the second given (away from January 1, 0001 00:00:00). * * @param minute second from January 1, 0001 00:00:00 * @return number of leap seconds that have occurred since second */ private static long getNumLeapSecsFromSec(long second) { int i = 0; long numLeapSeconds = 0; while (i < LEAP_SECONDS.length && LEAP_SECONDS[i++] <= second) numLeapSeconds++; return numLeapSeconds; } /* * Leap years are determined according to the following rule: * Every year that is exactly divisible by 4 is a leap year, * except for years that are exactly divisible by 100; * these centurial years are leap years only if they are exactly * divisible by 400. * * @param year the year that we want to determine is a leap year * @return whether or not the given year is a leap year */ private static boolean isLeapYear(long year) { if (year < YEAR_OFFSET) return false; return ((year % 4 == 0) && ((year % 100 != 0) || (year % 400 == 0))); } /* * Returns whether or not the given quantity of secs equates to a leap * second. * * @param sec quantity of seconds to determine is a leap second * @return whether or not the given quantity of seconds is a leap * second */ private static boolean isLeapSecond(long secs) { for (int ii = 0; ii < LEAP_SECONDS.length; ii++) { if (LEAP_SECONDS[ii] == secs) return true; } return false; } /* * Splits years into years by simply returning the given argument. * * @param years the year that we want to split * @return array whose first value is a year */ public static long[] splitYears(long years) { long[] result = new long[SPLIT_ARRAY_SIZE]; result[YEAR_INDEX] = years; return result; } /* * Splits given months into months and years. * * @param months the months that to split into years and months * @return array of split values (years, months) */ public static long[] splitMonths(long months) { long[] result = new long[SPLIT_ARRAY_SIZE]; // need to take the ceiling since this is a 1-based implementation result[YEAR_INDEX] = (long)Math.ceil((double)months / NUM_MONTHS_YEAR); result[MONTH_INDEX] = (months % NUM_MONTHS_YEAR == 0) ? NUM_MONTHS_YEAR : months % NUM_MONTHS_YEAR; return result; } /* * Splits given days into days, months and years. * * @param month the day that to split into days, months, years * @return array of split values (years, months, days) */ public static long[] splitDays(long days) { long gcCycleYears, centuryYears, leapCycleYears, years, months = 0; long[] result = new long[SPLIT_ARRAY_SIZE]; gcCycleYears = days / NUM_DAYS_GC_CYCLE; days -= gcCycleYears * NUM_DAYS_GC_CYCLE; centuryYears = days / NUM_DAYS_CENTURY; days -= centuryYears * NUM_DAYS_CENTURY; leapCycleYears = days / NUM_DAYS_LEAP_CYCLE; days -= leapCycleYears * NUM_DAYS_LEAP_CYCLE; // need to take the ceiling since this is a 1-based implementation years = (long)Math.ceil((double)days / NUM_DAYS_YEAR); years += gcCycleYears * NUM_YEARS_GC_CYCLE + centuryYears * NUM_YEARS_CENTURY + leapCycleYears * NUM_YEARS_LEAP_CYCLE; days = (days % NUM_DAYS_YEAR == 0) ? isLeapYear(years) ? NUM_DAYS_LEAP_YEAR : NUM_DAYS_YEAR : days - (days / NUM_DAYS_YEAR) * NUM_DAYS_YEAR; int ii = isLeapYear(years) ? LEAP_YEAR : NON_LEAP_YEAR; int jj; for (jj = 1; jj < DAYS_COMPLETED_BY_MONTH[ii].length; jj++) { if (days <= DAYS_COMPLETED_BY_MONTH[ii][jj]) { months = jj; break; } } days -= DAYS_COMPLETED_BY_MONTH[ii][jj - 1]; result[YEAR_INDEX] = years; result[MONTH_INDEX] = months; result[DAY_INDEX] = days; return result; } /* * Splits given hours into hours, days, months and years. * * @param hours the hours to split into hours, days, months, years * @return array of split values (years, months, days, hours) */ public static long[] splitHours(long hours) { long days; days = (long)Math.ceil((double)hours / NUM_HOURS_DAY); hours = (hours % NUM_HOURS_DAY == 0) ? NUM_HOURS_DAY : hours % NUM_HOURS_DAY; long[] result = splitDays(days); result[HOUR_INDEX] = hours; return result; } /* * Splits given minutes into minutes, hours, days, months and years. * * @param mins the minutes to split into minutes, hours, days, months, * years * @return array of split values (years, months, days, hours, * minutes) */ public static long[] splitMinutes(long mins) { long hours; hours = (long)Math.ceil((double)mins / NUM_MINS_HOUR); mins = (mins % NUM_MINS_HOUR == 0) ? NUM_MINS_HOUR : mins % NUM_MINS_HOUR; long[] result = splitHours(hours); result[MINUTE_INDEX] = mins; return result; } /* * Splits given seconds into seconds, minutes, hours, days, months and years. * * @param secs the seconds to split into seconds, minutes, hours, days, * months, years * @return array of split values (years, months, days, hours, * minutes, seconds) */ public static long[] splitSeconds(long secs) { long mins; // adjust secs given by number of leap secs that have occurred up to secs long numLeapSecs = getNumLeapSecsFromSec(secs); long origSecs = secs; secs -= numLeapSecs; mins = (long)Math.ceil((double)secs / NUM_SECS_MINUTE); secs = (secs % NUM_SECS_MINUTE == 0) ? NUM_SECS_MINUTE : secs % NUM_SECS_MINUTE; long[] result = splitMinutes(mins); result[SECOND_INDEX] = isLeapSecond(origSecs) ? 61 : secs; return result; } /* * Return the total number of days (inclusive) in this date starting at * January 1, 0001 to the date given in year, month, day. *
* Formula: * numDays = number of days in the completed years (e.g. if we are in year * 1978, we have completed 1977 years according to start of * this calendar) * + number of leap days that occurred in year's time (years / 4) * - number of non-400-divisible centurial years in year's time * + number of days completed in given year up to the given month * + day. * * @param year the year to turn into days * @param month the month to turn into days * @param day the day to turn into days * @return sum of the days in the three granularities combined */ private static long sumDays(long year, long month, long day) { long days; // using 'year - YEAR_OFFSET' here because we want to include all // completed years in this calculation (so the current year - 1 // since the given year is not yet complete) days = ((year - YEAR_OFFSET) * NUM_DAYS_YEAR) + ((year - YEAR_OFFSET) / NUM_YEARS_LEAP_CYCLE) - (((year - YEAR_OFFSET) / NUM_YEARS_CENTURY) - ((year - YEAR_OFFSET) / NUM_YEARS_GC_CYCLE)); // using 'month - MONTH_OFFSET' for the same reason as above days += isLeapYear(year) ? DAYS_COMPLETED_BY_MONTH[LEAP_YEAR][new Long(month).intValue() - MONTH_OFFSET] : DAYS_COMPLETED_BY_MONTH[NON_LEAP_YEAR][new Long(month).intValue() - MONTH_OFFSET]; days += day; return days; } /* * Return the total number of minutes (inclusive) in this date starting at * January 1, 0001 00:00 to the date given in year, month, day, hour and * minute. *
* Formula: * numMinutes = number of completed days * 1440 (NUM_MINS_DAY) * + number of completed days * 60 (NUM_MINS_HOUR) * + number of minutes given * + 1 (MINUTE_OFFSET) since counting at minutes starts at 0 * and this method should be inclusive * * @param year the year to turn into minutes * @param month the month to turn into minutes * @param day the day to turn into minutes * @param hour the hour to turn into minutes * @param minute the minute to turn into minutes * @return sum of the minutes in the five granularities combined */ public static long sumMinutes(long year, long month, long day, long hour, long minute) { long days; days = sumDays(year, month, day) - DAY_OFFSET; return days * NUM_MINS_DAY + hour * NUM_MINS_HOUR + minute + MINUTE_OFFSET; } /* * Return the total number of seconds (inclusive) in this date starting at * January 1, 0001 00:00:00 to the date given in year, month, day, hour, * minute, and second. *
* Formula: * numSeconds = number of completed minutes * 60 (NUM_SECS_MINUTE) * + number of seconds given * + 1 (SECOND_OFFSET) since counting at seconds starts at 0 * and this method should be inclusive * + number of leap seconds that have occurred up to this date * * @param year the year to turn into seconds * @param month the month to turn into seconds * @param day the day to turn into seconds * @param hour the hour to turn into seconds * @param minute the minute to turn into seconds * @param second the second to turn into seconds * @return sum of the seconds in the six granularities combined */ private static long sumSeconds(long year, long month, long day, long hour, long minute, long second) { long minutes; minutes = sumMinutes(year, month, day, hour, minute) - MINUTE_OFFSET; return minutes * NUM_SECS_MINUTE + second + SECOND_OFFSET + getNumLeapSecsFromMin(minutes); } public static long castDayToYear(Long dayL){ return castDayToYear(dayL.longValue()); } /* * Covert the given amount of seconds to minutes using the cast operation. * This method does take leap seconds into account. *
* Formula: * numSeconds = the number of gregorian cycles in day * + the number of centuries in the remainding days * + the number of leap cycle years in the remainding days * + the number of years in the remainding days * + 1 (if there are any days remainding) * * @param day number of day granules to cast into year granularity * @return number of year granules */ public static long castDayToYear(long day) { long cycleYears, centuryYears, leapCycleYears, yearYears; long remaindingDays; cycleYears = day / NUM_DAYS_GC_CYCLE * NUM_YEARS_GC_CYCLE; remaindingDays = day - (day / NUM_DAYS_GC_CYCLE * NUM_DAYS_GC_CYCLE); centuryYears = remaindingDays / NUM_DAYS_CENTURY * NUM_YEARS_CENTURY; remaindingDays -= remaindingDays / NUM_DAYS_CENTURY * NUM_DAYS_CENTURY; leapCycleYears = remaindingDays / NUM_DAYS_LEAP_CYCLE * NUM_YEARS_LEAP_CYCLE; remaindingDays -= remaindingDays / NUM_DAYS_LEAP_CYCLE * NUM_DAYS_LEAP_CYCLE; yearYears = remaindingDays / NUM_DAYS_YEAR; remaindingDays -= remaindingDays / NUM_DAYS_YEAR * NUM_DAYS_YEAR; return cycleYears + centuryYears + leapCycleYears + yearYears + (remaindingDays > 0 ? 1 : 0); } /***************************************************************************/ /* Methods that will be used for the irregular mappings in this calendar */ /***************************************************************************/ public static long castSecondToMinute(Long secondL){ return castSecondToMinute(secondL.longValue()); } /* * Covert the given amount of seconds to minutes using the cast operation. * This method does take leap seconds into account. *
* Formula: * numMinutes = ceil((numSeconds - number of leap seconds that have * occurred up to and including this second) * / 60 [number of seconds in a minute]) * * @param second number of second granules to cast into minute granularity * @return number of minute granules */ public static long castSecondToMinute(long second) { long leapSeconds = 0; leapSeconds = getNumLeapSecsFromSec(second); return (long)Math.ceil((second - leapSeconds) / 60.0); } public static long castMinuteToSecond(Long minuteL){ return castMinuteToSecond(minuteL.longValue()); } /* * Covert the given amount of minutes to seconds using the cast operation. * This method does take leap seconds into account. *
* Formula: * numSeconds = the number of minutes totally complete * number of seconds * in a minute + 1 (to roll over to the lower support of minute) * * @param second number of minute granules to cast into second granularity * @return number of second granules */ public static long castMinuteToSecond(long minute) { long seconds; seconds = (NUM_SECS_MINUTE * (minute - 1)) + 1; return seconds += getNumLeapSecsFromMin(minute); } public static long castDayToMonth(Long dayL){ return castDayToMonth(dayL.longValue()); } /* * Convert the given amount of days to months using the cast operation. * This method does take leap years into account. *
* Formula: * numMonths = number of years completed in day * 12 + remainding months * * @param day number of day granules to cast into month granularity * @return number of month granules */ public static long castDayToMonth(long day) { long cycleYears, centuryYears, leapCycleYears, yearYears, totalYears; long remaindingDays; long months = 0; // get number of years completed by this day using the algorithm from // castDayToYear() cycleYears = day / NUM_DAYS_GC_CYCLE * NUM_YEARS_GC_CYCLE; remaindingDays = day - (day / NUM_DAYS_GC_CYCLE * NUM_DAYS_GC_CYCLE); centuryYears = remaindingDays / NUM_DAYS_CENTURY * NUM_YEARS_CENTURY; remaindingDays -= remaindingDays / NUM_DAYS_CENTURY * NUM_DAYS_CENTURY; leapCycleYears = remaindingDays / NUM_DAYS_LEAP_CYCLE * NUM_YEARS_LEAP_CYCLE; remaindingDays -= remaindingDays / NUM_DAYS_LEAP_CYCLE * NUM_DAYS_LEAP_CYCLE; yearYears = remaindingDays / NUM_DAYS_YEAR; remaindingDays -= remaindingDays / NUM_DAYS_YEAR * NUM_DAYS_YEAR; totalYears = cycleYears + centuryYears + leapCycleYears + yearYears; // if there are still days remainding, using DAYS_COMPLETED_BY_MONTH, // figure out how many months are in the remainding days if (remaindingDays > 0) { int i = isLeapYear(totalYears + 1) ? LEAP_YEAR : NON_LEAP_YEAR; for (int j = 1; j < DAYS_COMPLETED_BY_MONTH[i].length; j++) { if (remaindingDays < DAYS_COMPLETED_BY_MONTH[i][j]) { months = j; break; } } } // now add to months the total number of months in all of the completed // years return months + totalYears * NUM_MONTHS_YEAR; } public static long castMonthToDay(Long monthL){ return castMonthToDay(monthL.longValue()); } /* * Covert the given amount of months to days using the cast operation. * This method does take leap years into account. *
* Formula:
* numMonths = number of days in completed years + days up to this
* month + 1 (to get the first day of this month since
* this would be the lower bound of a scale operation -
* and thus the correct behavior of cast)
*
* @param month number of month granules to cast into day granularity
* @return number of day granules
*/
public static long castMonthToDay(long month)
{
long cycleYears, centuryYears, leapCycleYears, yearYears;
long remaindingMonths;
long year;
long days = 0;
month -= MONTH_OFFSET;
cycleYears = month / NUM_MONTHS_GC_CYCLE;
remaindingMonths = month - (month / NUM_MONTHS_GC_CYCLE * NUM_MONTHS_GC_CYCLE);
centuryYears = remaindingMonths / NUM_MONTHS_CENTURY;
remaindingMonths -= remaindingMonths / NUM_MONTHS_CENTURY * NUM_MONTHS_CENTURY;
leapCycleYears = remaindingMonths / NUM_MONTHS_LEAP_CYCLE;
remaindingMonths -= remaindingMonths / NUM_MONTHS_LEAP_CYCLE * NUM_MONTHS_LEAP_CYCLE;
yearYears = remaindingMonths / NUM_MONTHS_YEAR;
remaindingMonths -= remaindingMonths / NUM_MONTHS_YEAR * NUM_MONTHS_YEAR;
if (remaindingMonths > 0)
{
// figure out what year this number of months is in
year = (long) Math.ceil(month / 12.0);
int i = isLeapYear(year) ? LEAP_YEAR : NON_LEAP_YEAR;
for (int j = 0; j < remaindingMonths; j++)
days += DAYS_IN_MONTHS[i][j];
}
return days += (cycleYears * NUM_DAYS_GC_CYCLE) + (centuryYears * NUM_DAYS_CENTURY)
+ (leapCycleYears * NUM_DAYS_LEAP_CYCLE) + (yearYears * NUM_DAYS_YEAR) + 1;
}
/**
* Fills each Field of Fields, which can only be produced
* by either InstantOutputFormat or IntervalOutputFormat properties.
*
* @param granule Granule, which contains timestamp information
* @param fields Fields, which represents unparsed temporal constant
*
* @return a boolean value true if conversion is successfull, false otherwise
*
* @throws CalendarServiceException if any abnormal condition occurs when converting
* timestamp to unparsed temporal constant. Unsupported Granularities or
* Properties, which Fields is produced, may cause
* this exception.
*/
static public Boolean granuleToFields(Granule granule, Fields fields) throws CalendarServiceException{
long splitResults[];
String granularityName = granule.getGranularity().getLocalName();
// according to granularity of timestamp flattened it to upper granularities
if(granularityName.equals("year"))
splitResults = splitYears(granule.getGranule().getValue());
else if(granularityName.equals("month"))
splitResults = splitMonths(granule.getGranule().getValue());
else if(granularityName.equals("day"))
splitResults = splitDays(granule.getGranule().getValue());
else if(granularityName.equals("hour"))
splitResults = splitHours(granule.getGranule().getValue());
else if(granularityName.equals("minute"))
splitResults = splitMinutes(granule.getGranule().getValue());
else if(granularityName.equals("second")){
splitResults = splitSeconds(granule.getGranule().getValue());
System.out.println("splitted granule: " + granule.image()
+ splitResults[SECOND_INDEX] + "/" + splitResults[MINUTE_INDEX] +
"/" + splitResults[HOUR_INDEX] + "/" + splitResults[DAY_INDEX] +
"/" + splitResults[MONTH_INDEX] + "/" + splitResults[YEAR_INDEX]);
}
else
throw new CalendarServiceException("Exception when converting granule to fields: " +
" undefined granularity: " + granularityName + " in ADGregorian Calendar.");
// all the fields corresponding to all the granularities and additional
// field names of ADGregorian calendar
Field yearField = fields.getFieldByName("year"),
monthField = fields.getFieldByName("month"),
dayField = fields.getFieldByName("day"),
hourField = fields.getFieldByName("hour"),
minuteField = fields.getFieldByName("minute"),
secondField = fields.getFieldByName("second"),
monthOfYearField = fields.getFieldByName("monthOfYear"),
dayOfMonthField = fields.getFieldByName("dayOfMonth"),
hourOfDayField = fields.getFieldByName("hourOfDay"),
minuteOfHourField = fields.getFieldByName("minuteOfHour"),
secondOfMinuteField = fields.getFieldByName("secondOfMinute");
// multiplexing of output formats, compatibility checks between fields
// are not handled yet
if(fields.getName().equals("InstantOutputFormat")){
if(yearField != null) yearField.setValue(splitResults[YEAR_INDEX]);
if(monthField != null) monthField.setValue(splitResults[MONTH_INDEX]);
if(dayField != null) dayField.setValue(splitResults[DAY_INDEX]);
if(hourField != null) hourField.setValue(splitResults[HOUR_INDEX]);
if(minuteField != null) minuteField.setValue(splitResults[MINUTE_INDEX]);
if(secondField != null) secondField.setValue(splitResults[SECOND_INDEX]);
if(monthOfYearField != null) monthOfYearField.setValue(splitResults[MONTH_INDEX]);
if(dayOfMonthField != null) dayOfMonthField.setValue(splitResults[DAY_INDEX]);
if(hourOfDayField != null) hourOfDayField.setValue(splitResults[HOUR_INDEX]);
if(minuteOfHourField != null) minuteOfHourField.setValue(splitResults[MINUTE_INDEX]);
if(secondOfMinuteField != null) secondOfMinuteField.setValue(splitResults[SECOND_INDEX]);
}
else if(fields.getName().equals("IntervalOutputFormat")){
if(yearField != null) yearField.setValue(splitResults[YEAR_INDEX]);
if(monthField != null) monthField.setValue(splitResults[MONTH_INDEX]);
if(dayField != null) dayField.setValue(splitResults[DAY_INDEX]);
if(hourField != null) hourField.setValue(splitResults[HOUR_INDEX]);
if(minuteField != null) minuteField.setValue(splitResults[MINUTE_INDEX]);
if(secondField != null) secondField.setValue(splitResults[SECOND_INDEX]);
}
else
throw new CalendarServiceException("Exception when converting Granule to fill Fields: undefined temporal data type " +
fields.getName());
return new Boolean(true);
}
/**
* Converts unparsed temporal constant, Fields, into timestamp, Granule
* Fields, which can only be produced by either InstantOutputFormat or
* IntervalOutputFormat properties.
*
* @param fields Fields, which represents unparsed temporal constant
*
* @return a Granule, which is the corresponding timestamp
*
* @throws CalendarServiceException if any abnormal condition occurs when converting
* unparsed temporal constant to timestamp. Unsupported Granularities or
* Properties, which Fields is produced, may cause
* this exception.
*/
static public Granule fieldsToGranule(Fields fields) throws CalendarServiceException{
// all the fields corresponding to all the granularities and additional
// field names of ADGregorian calendar
Field yearField = fields.getFieldByName("year"),
monthField = fields.getFieldByName("month"),
dayField = fields.getFieldByName("day"),
hourField = fields.getFieldByName("hour"),
minuteField = fields.getFieldByName("minute"),
secondField = fields.getFieldByName("second"),
monthOfYearField = fields.getFieldByName("monthOfYear"),
dayOfMonthField = fields.getFieldByName("dayOfMonth"),
hourOfDayField = fields.getFieldByName("hourOfDay"),
minuteOfHourField = fields.getFieldByName("minuteOfHour"),
secondOfMinuteField = fields.getFieldByName("secondOfMinute");
// declare variables for values of granularities and additional field names/
// should sumDays, sum... methods take long or int ???
long secondOfMinute = 0, minuteOfHour = 0, hourOfDay = 0, dayOfMonth = 0, monthOfYear = 0,
year = 0, month = 0, day = 0, minute = 0, second = 0, hour = 0;
// get each granularity or additional field values from fields
if(yearField != null) year = yearField.getValue();
if(monthField != null) month = monthField.getValue();
if(dayField != null) day = dayField.getValue();
if(hourField != null) hour = hourField.getValue();
if(minuteField != null) minute = minuteField.getValue();
if(secondField != null) second = secondField.getValue();
if(monthOfYearField != null) monthOfYear = monthOfYearField.getValue();
if(dayOfMonthField != null) dayOfMonth = dayOfMonthField.getValue();
if(hourOfDayField != null) hourOfDay = hourOfDayField.getValue();
if(minuteOfHourField != null) minuteOfHour = minuteOfHourField.getValue();
if(secondOfMinuteField != null) secondOfMinute = secondOfMinuteField.getValue();
// multiplexing of input formats, compatibility checks between fields
// are not handled yet
// Note that we don't accept "5 hour" or "hour 4, day 2, month 3" or
// "second 2, hour 1, day 2, month 3" as valid instants. They should
// an instant in granularity X, should include valid granules for all its
// coarser granularities.
if(fields.getName().equals("InstantInputFormat")){
long sum = 0;
if(dayOfMonthField != null && monthOfYearField != null && yearField != null
&& hourOfDayField != null && minuteOfHourField != null && secondOfMinuteField != null){
sum = sumSeconds(year, monthOfYear, dayOfMonth, hourOfDay, minuteOfHour, secondOfMinute);
//System.out.println(secondOfMinute + "/" + minuteOfHour + "/" + hourOfDay + "/" + dayOfMonth
// + "/" + monthOfYear + "/" + year + "->" + sum);
return new Granule(new Granularity("second"), sum);
}
if(dayOfMonthField != null && monthOfYearField != null && yearField != null
&& hourOfDayField != null && minuteOfHourField != null){
sum = sumMinutes(year, monthOfYear, dayOfMonth, hourOfDay, minuteOfHour);
return new Granule(new Granularity("minute"), sum);
}
if(dayOfMonthField != null && monthOfYearField != null && yearField != null
&& hourOfDayField != null){
sum = (sumDays(year, monthOfYear, dayOfMonth) - DAY_OFFSET) * NUM_HOURS_DAY + hourOfDay;
return new Granule(new Granularity("hour"), sum);
}
if(dayOfMonthField != null && monthOfYearField != null && yearField != null){
sum = sumDays(year, monthOfYear, dayOfMonth);
return new Granule(new Granularity("day"), sum);
}
if(monthOfYearField != null && yearField != null){
sum = (year - YEAR_OFFSET) * NUM_MONTHS_YEAR + monthOfYear;
return new Granule(new Granularity("month"), sum);
}
if(yearField != null){
sum = year;
return new Granule(new Granularity("year"), sum);
}
}
else if(fields.getName().equals("IntervalInputFormat")){
long sum = 0;
// we have to note that when we sum "5 seconds, 4 hours, 5 days, 2 years" into seconds
// we can't use sum methods above since they use offset to adjust to instant semantic
// on the other hand, we need interval cast and scale methods, which we don't have. Therefore
// we'll go with sum methods
if(secondField != null ) {
sum = sumSeconds(year, month, day, hour, minute, second);
return new Granule(new Granularity("second"), sum);
}
if(minuteField != null) {
sum = sumMinutes(year, month, day, hour, minute);
return new Granule(new Granularity("minute"), sum);
}
if(hourField != null){
sum = (sumDays(year, month, day) - DAY_OFFSET) * NUM_HOURS_DAY + hour;
return new Granule(new Granularity("hour"), sum);
}
if(dayField != null){
sum = sumDays(year, month, day);
return new Granule(new Granularity("day"), sum);
}
if(monthField != null){
sum = (year - YEAR_OFFSET) * NUM_MONTHS_YEAR + month;
return new Granule(new Granularity("month"), sum);
}
if(yearField != null) {
sum = year;
return new Granule(new Granularity("year"), sum);
}
}
throw new CalendarServiceException("Exception when converting Fields to Granule: undefined temporal data type " +
fields.getName() + " or unidentified field values in temporal constant ");
}
public static void main(String[] args)
{
long [] splitResults;
/*
// ********************** test sumDays **********************
System.out.println("\n********************** test sumDays **********************");
System.out.println("January 1, 0001 in days = " + sumDays(1, 1, 1)); // 1
System.out.println("December 31, 0001 in days = " + sumDays(1, 12, 31)); // 365
System.out.println("December 31, 0004 in days = " + sumDays(4, 12, 31)); // 1461
System.out.println("February 15, 0001 in days = " + sumDays(1, 2, 15)); // 46
System.out.println("December 31, 0100 in days = " + sumDays(100, 12, 31)); // 36524
System.out.println("December 31, 0400 in days = " + sumDays(400, 12, 31)); // 146097
System.out.println("March 20, 0400 in days = " + sumDays(400, 3, 20)); // 145811
System.out.println("November 4, 1101 in days = " + sumDays(1101, 11, 4)); // 402074
System.out.println("July 11, 1978 in days = " + sumDays(1978, 7, 11)); // 722276
System.out.println("September 2, 2000 in days = " + sumDays(2000, 9, 2)); // 730365
System.out.println("September 19, 2003 in days = " + sumDays(2003, 9, 19)); // 731477
System.out.println("August 21, 2000 in days = " + sumDays(2000, 8, 21)); // 1053326000
// ********************** test castDayToYear **********************
System.out.println("\n********************** test castDayToYear **********************");
System.out.println("cast(1 day(s), years) = " + castDayToYear(1) + " year(s)"); // 1
System.out.println("cast(365 day(s), years) = " + castDayToYear(365) + " year(s)"); // 1
System.out.println("cast(1461 day(s), years) = " + castDayToYear(1461) + " year(s)"); // 4
System.out.println("cast(46 day(s), years) = " + castDayToYear(46) + " year(s)"); // 1
System.out.println("cast(36524 day(s), years) = " + castDayToYear(36524) + " year(s)"); // 100
System.out.println("cast(146097 day(s), years) = " + castDayToYear(146097) + " year(s)"); // 400
System.out.println("cast(145811 day(s), years) = " + castDayToYear(145811) + " year(s)"); // 400
System.out.println("cast(402074 day(s), years) = " + castDayToYear(402074) + " year(s)"); // 1101
System.out.println("cast(722276 day(s), years) = " + castDayToYear(722276) + " year(s)"); // 1978
System.out.println("cast(730365 day(s), years) = " + castDayToYear(730365) + " year(s)"); // 2000
System.out.println("cast(731477 day(s), years) = " + castDayToYear(731477) + " year(s)"); // 2003
// ********************** test castDayToMonth **********************
System.out.println("\n********************** test castDayToMonth **********************");
System.out.println("cast(1 day(s), months) = " + castDayToMonth(1) + " month(s)"); // 1 [January 1, 0001 ->
January 0001]
System.out.println("cast(365 day(s), months) = " + castDayToMonth(365) + " month(s)"); // 12 [December 31, 0001 ->
December 0001]
System.out.println("cast(1461 day(s), months) = " + castDayToMonth(1461) + " month(s)"); // 48 [December 31, 0004 ->
December 0004]
System.out.println("cast(46 day(s), months) = " + castDayToMonth(46) + " month(s)"); // 2 [February 15, 0001 ->
February 0001]
System.out.println("cast(36524 day(s), months) = " + castDayToMonth(36524) + " month(s)"); // 1200 [December 31, 0100 ->
December 0100]
System.out.println("cast(146097 day(s), months) = " + castDayToMonth(146097) + " month(s)"); // 4800 [December 31, 0400 ->
December 0400]
System.out.println("cast(145811 day(s), months) = " + castDayToMonth(145811) + " month(s)"); // 4791 [March 20, 0400 -> March
0400]
System.out.println("cast(402074 day(s), months) = " + castDayToMonth(402074) + " month(s)"); // 13211 [November 4, 1101 ->
November 1101]
System.out.println("cast(722276 day(s), months) = " + castDayToMonth(722276) + " month(s)"); // 23731 [July 11, 1978 -> July
1978]
System.out.println("cast(730365 day(s), months) = " + castDayToMonth(730365) + " month(s)"); // 23997 [September 2, 2000 ->
September 2000]
System.out.println("cast(731477 day(s), months) = " + castDayToMonth(731477) + " month(s)"); // 24033 [September 19, 2003 ->
September 2003]
// ********************** test castMonthToDay **********************
System.out.println("\n********************** test castMonthToDay **********************");
System.out.println("cast(1 month(s), days) = " + castMonthToDay(1) + " day(s) [should equal "
+ sumDays(1, 1, 1) + "]"); // 1 [January 0001 -> January 1, 0001]
System.out.println("cast(12 month(s), days) = " + castMonthToDay(12) + " days(s) [should equal "
+ sumDays(1, 12, 1) + "]"); // 335 [December 0001 -> December 1, 0001]
System.out.println("cast(48 month(s), days) = " + castMonthToDay(48) + " days(s) [should equal "
+ sumDays(4, 12, 1) + "]"); // 1431 [December 0004 -> December 1, 0004]
System.out.println("cast(2 month(s), days) = " + castMonthToDay(2) + " days(s) [should equal "
+ sumDays(1, 2, 1) + "]"); // 32 [February 0001 -> February 1, 0001]
System.out.println("cast(1200 month(s), days) = " + castMonthToDay(1200) + " days(s) [should equal "
+ sumDays(100, 12, 1) + "]"); // 36494 [December 0100 -> December 1, 0100]
System.out.println("cast(4800 month(s), days) = " + castMonthToDay(4800) + " days(s) [should equal "
+ sumDays(400, 12, 1) + "]"); // 146067 [December 0400 -> December 1, 0400]
System.out.println("cast(4791 month(s), days) = " + castMonthToDay(4791) + " days(s) [should equal "
+ sumDays(400, 3, 1) + "]"); // 145792 [March 0400 -> March 1, 0400]
System.out.println("cast(13211 month(s), days) = " + castMonthToDay(13211) + " days(s) [should equal "
+ sumDays(1101, 11, 1) + "]"); // 402071 [November 1101 -> November 1, 1101]
System.out.println("cast(23731 month(s), days) = " + castMonthToDay(23731) + " days(s) [should equal "
+ sumDays(1978, 7, 1) + "]"); // 722266 [July 1978 -> July 1, 1978]
System.out.println("cast(23997 month(s), days) = " + castMonthToDay(23997) + " days(s) [should equal "
+ sumDays(2000, 9, 1) + "]"); // 730364 [September 2000 -> September 1, 2000]
System.out.println("cast(24033 month(s), days) = " + castMonthToDay(24033) + " days(s) [should equal "
+ sumDays(2003, 9, 1) + "]"); // 731459 [September 2003 -> September 1, 2003]
// ********************** test sumSeconds **********************
System.out.println("\n********************** test sumSeconds **********************");
System.out.println("January 1, 0001 00:00:00 in seconds = " + sumSeconds(1, 1, 1, 0, 0, 0)); // 1
System.out.println("December 31, 0001 00:00:00 in seconds = " + sumSeconds(1, 12, 31, 0, 0, 0)); // 31449601
System.out.println("December 31, 0004 00:00:00 in seconds = " + sumSeconds(4, 12, 31, 0, 0, 0)); // 126144001
System.out.println("February 15, 0001 00:00:00 in seconds = " + sumSeconds(1, 2, 15, 0, 0, 0)); // 3888001
System.out.println("December 31, 0100 00:00:00 in seconds = " + sumSeconds(100, 12, 31, 0, 0, 0)); // 3155587201
System.out.println("December 31, 0400 00:00:00 in seconds = " + sumSeconds(400, 12, 31, 0, 0, 0)); // 12622694401
System.out.println("March 20, 0400 00:00:00 in seconds = " + sumSeconds(400, 3, 20, 0, 0, 0)); // 12597984001
System.out.println("November 4, 1101 00:00:00 in seconds = " + sumSeconds(1101, 11, 4, 0, 0, 0)); // 34739107201
System.out.println("July 11, 1978 23:47:00 in seconds = " + sumSeconds(1978, 7, 11, 23, 47, 11)); // 62404645639
System.out.println("September 2, 2000 00:00:00 in seconds = " + sumSeconds(2000, 9, 2, 0, 0, 0)); // 63103449623
System.out.println("September 19, 2003 00:00:00 in seconds = " + sumSeconds(2003, 9, 19, 0, 0, 0));
System.out.println("January 1, 1970 00:00:00 in seconds = " + sumSeconds(1970, 1, 1, 0, 0, 0));
System.out.println("\n------------ these values are used in the test below ------------");
System.out.println("January 1, 0001 00:00:00 in seconds = " + sumSeconds(1, 1, 1, 0, 0, 0)); // 1
System.out.println("January 1, 0001 00:00:33 in seconds = " + sumSeconds(1, 1, 1, 0, 0, 33)); // 34
System.out.println("March 20, 0400 19:02:15 in seconds = " + sumSeconds(400, 3, 20, 19, 2, 15)); // 12598052536
System.out.println("November 4, 1101 12:30:05 in seconds = " + sumSeconds(1101, 11, 4, 12, 30, 5)); // 34739152206
System.out.println("June 30, 1972 23:59:60 in seconds = " + sumSeconds(1972, 6, 30, 23, 59, 60)); // 62214393601
System.out.println("January 1, 1973 4:57:04 in seconds = " + sumSeconds(1973, 1, 1, 4, 57, 04)); // 62230309027
System.out.println("July 11, 1978 23:47:11 in seconds = " + sumSeconds(1978, 7, 11, 23, 47, 11)); // 62404645639
System.out.println("September 19, 2003 09:19:19 in seconds = " + sumSeconds(2003, 9, 19, 9, 19, 19)); // 63199559982
// ********************** test sumMinutes **********************
System.out.println("\n********************** test sumMinutes **********************");
System.out.println("January 1, 0001 00:00 in minutes = " + sumMinutes(1, 1, 1, 0, 0)); // 1
System.out.println("December 31, 0001 00:00 in minutes = " + sumMinutes(1, 12, 31, 0, 0)); // 524161
System.out.println("December 31, 0004 00:00 in minutes = " + sumMinutes(4, 12, 31, 0, 0)); // 2102401
System.out.println("February 15, 0001 00:00 in minutes = " + sumMinutes(1, 2, 15, 0, 0)); // 64801
System.out.println("December 31, 0100 00:00 in minutes = " + sumMinutes(100, 12, 31, 0, 0)); // 52593121
System.out.println("December 31, 0400 00:00 in minutes = " + sumMinutes(400, 12, 31, 0, 0)); // 210378241
System.out.println("March 20, 0400 02:41 in minutes = " + sumMinutes(400, 3, 20, 2, 41)); // 209966562
System.out.println("November 4, 1101 00:00 in minutes = " + sumMinutes(1101, 11, 4, 0, 0)); // 578985121
System.out.println("July 11, 1978 23:47 in minutes = " + sumMinutes(1978, 7, 11, 23, 47)); // 1040077428
System.out.println("September 2, 2000 00:00 in minutes = " + sumMinutes(2000, 9, 2, 0, 0)); // 1051724161
System.out.println("September 19, 2003 00:00 in minutes = " + sumMinutes(2003, 9, 19, 0, 0)); // 1053325441
System.out.println("August 21, 2000 07:00 in minutes = " + sumMinutes(2000, 8, 21, 7, 00)); // 1053326000
System.out.println("\n------------ these values are used in the test below ------------");
System.out.println("January 1, 0001 00:00 in minutes = " + sumMinutes(1, 1, 1, 0, 0)); // 1
System.out.println("January 1, 0001 00:01 in minutes = " + sumMinutes(1, 1, 1, 0, 1)); // 2
System.out.println("March 20, 0400 02:41 in minutes = " + sumMinutes(400, 3, 20, 2, 41)); // 134229762
System.out.println("July 1, 1972 00:01 in minutes = " + sumMinutes(1972, 7, 1, 0, 1)); // 1036906562
System.out.println("January 1, 1973 4:57 in minutes = " + sumMinutes(1973, 1, 1, 4, 57)); // 1037171818
System.out.println("July 11, 1978 23:47 in minutes = " + sumMinutes(1978, 7, 11, 23, 47)); // 1040077428
System.out.println("September 19, 2003 09:19 in minutes = " + sumMinutes(2003, 9, 19, 9, 19)); // 1053326000
// ******************* test castMinuteToSecond *****************
System.out.println("\n********************** test castMinuteToSecond **********************");
System.out.println("cast(1 minute(s), seconds) = " + castMinuteToSecond(1)
+ " second(s) [should equal " + sumSeconds(1, 1, 1, 0, 0, 0) + "]"); // 1 [January 1, 0001 00:00
-> January 1, 0001 00:00:00]
System.out.println("cast(2 minute(s), seconds) = " + castMinuteToSecond(2)
+ " second(s) [should equal " + sumSeconds(1, 1, 1, 0, 1, 0) + "]"); // 61 [January 1, 0001 00:01
-> January 1, 0001 00:01:00]
System.out.println("cast(209966562 minute(s), seconds) = " + castMinuteToSecond(209966562)
+ " second(s) [should equal " + sumSeconds(400, 3, 20, 2, 41, 0) + "]"); // 12597993661 [March 20, 0400 02:41
-> March 20, 0400 02:41:00]
System.out.println("cast(1036906562 minute(s), seconds) = " + castMinuteToSecond(1036906562)
+ " second(s) [should equal " + sumSeconds(1972, 7, 1, 0, 1, 0) + "]"); // 62214393662 [July 1, 1972 00:01
-> July 1, 1972 00:01:00]
System.out.println("cast(1037171818 minute(s), seconds) = " + castMinuteToSecond(1037171818)
+ " second(s) [should equal " + sumSeconds(1973, 1, 1, 4, 57, 0) + "]"); // 62230309023 [January 1, 1973 4:57
-> January 1, 1973 4:57:00]
System.out.println("cast(1040077428 minute(s), seconds) = " + castMinuteToSecond(1040077428)
+ " second(s) [should equal " + sumSeconds(1978, 7, 11, 23, 47, 0) + "]"); // 62404645628 [July 11, 1978 23:47
-> July 11, 1978 23:47:00]
System.out.println("cast(1053326000 minute(s), seconds) = " + castMinuteToSecond(1053326000)
+ " second(s) [should equal " + sumSeconds(2003, 9, 19, 9, 19, 0) + "]"); // 63199559963 [September 19, 2003
09:19 -> September 19, 2003 09:19:00]
// ******************* test castSecondToMinute *****************
System.out.println("\n********************** test castSecondToMinute **********************");
System.out.println("cast(1 second(s), minutes) = " + castSecondToMinute(1)
+ " second(s) [should equal " + sumMinutes(1, 1, 1, 0, 0) + "]"); // 1 [January 1, 0001 00:00:00
-> January 1, 0001 00:00]
System.out.println("cast(34 second(s), minutes) = " + castSecondToMinute(34)
+ " second(s) [should equal " + sumMinutes(1, 1, 1, 0, 0) + "]"); // 61 [January 1, 0001 00:00:33
-> January 1, 0001 00:00]
System.out.println("cast(12598052536 second(s), minutes) = " + castSecondToMinute(12598052536L)
+ " second(s) [should equal " + sumMinutes(400, 3, 20, 19, 2) + "]"); // 12597993661 [March 20, 0400 19:02:15
-> March 20, 0400 19:02]
System.out.println("cast(34739152206 second(s), minutes) = " + castSecondToMinute(34739152206L)
+ " second(s) [should equal " + sumMinutes(1101, 11, 4, 12, 30) + "]"); // 62214393662 [November 4, 1101
12:30:05 -> November 4, 1101 12:30]
System.out.println("cast(62214393601 second(s), minutes) = " + castSecondToMinute(62214393601L)
+ " second(s) [should equal " + sumMinutes(1972, 6, 30, 23, 59) + "]"); // 62230309023 [June 30, 1972 23:59:60
-> June 30, 1972 23:59]
System.out.println("cast(62230309027 second(s), minutes) = " + castSecondToMinute(62230309027L)
+ " second(s) [should equal " + sumMinutes(1973, 1, 1, 4, 57) + "]"); // 62404645628 [January 1, 1973 4:57:04
-> January 1, 1973 4:57]
System.out.println("cast(62404645639 second(s), minutes) = " + castSecondToMinute(62404645639L)
+ " second(s) [should equal " + sumMinutes(1978, 7, 11, 23, 47) + "]"); // 63199559963 [July 11, 1978 23:47:11
-> July 11, 1978 23:47]
System.out.println("cast(63199559982 second(s), minutes) = " + castSecondToMinute(63199559982L)
+ " second(s) [should equal " + sumMinutes(2003, 9, 19, 9, 19) + "]"); // 63199559963 [September 19, 2003
09:19:19 -> September 19, 2003 09:19:19]
// ********************** test splitMonths**********************
System.out.println("\n********************** test splitMonths **********************");
splitResults = splitMonths(1);
System.out.println("1 month = " + splitResults[MONTH_INDEX] + " month(s), "
+ splitResults[YEAR_INDEX] + " year(s) [should be 1, 1]");
splitResults = splitMonths(1200);
System.out.println("1200 months = " + splitResults[MONTH_INDEX] + " month(s), "
+ splitResults[YEAR_INDEX] + " year(s) [should be 12, 100]");
splitResults = splitMonths(24033);
System.out.println("24033 months = " + splitResults[MONTH_INDEX] + " month(s), "
+ splitResults[YEAR_INDEX] + " year(s) [should be 9, 2003]");
// ********************** test splitDays **********************
System.out.println("\n********************** test splitDays **********************");
splitResults = splitDays(1);
System.out.println("1 day = " + splitResults[DAY_INDEX] + " days(s), "
+ splitResults[MONTH_INDEX] + " month(s), "
+ splitResults[YEAR_INDEX] + " year(s) [should be 1, 1, 1]");
splitResults = splitDays(31);
System.out.println("31 day = " + splitResults[DAY_INDEX] + " days(s), "
+ splitResults[MONTH_INDEX] + " month(s), "
+ splitResults[YEAR_INDEX] + " year(s) [should be 31, 1, 1]");
splitResults = splitDays(364);
System.out.println("364 day = " + splitResults[DAY_INDEX] + " days(s), "
+ splitResults[MONTH_INDEX] + " month(s), "
+ splitResults[YEAR_INDEX] + " year(s) [should be 30, 12, 1]");
splitResults = splitDays(365);
System.out.println("365 day = " + splitResults[DAY_INDEX] + " days(s), "
+ splitResults[MONTH_INDEX] + " month(s), "
+ splitResults[YEAR_INDEX] + " year(s) [should be 31, 12, 1]");
splitResults = splitDays(1461);
System.out.println("1461 day = " + splitResults[DAY_INDEX] + " days(s), "
+ splitResults[MONTH_INDEX] + " month(s), "
+ splitResults[YEAR_INDEX] + " year(s) [should be 31, 12, 4]");
splitResults = splitDays(46);
System.out.println("46 day = " + splitResults[DAY_INDEX] + " days(s), "
+ splitResults[MONTH_INDEX] + " month(s), "
+ splitResults[YEAR_INDEX] + " year(s) [should be 15, 2, 1]");
splitResults = splitDays(36524);
System.out.println("36524 day = " + splitResults[DAY_INDEX] + " days(s), "
+ splitResults[MONTH_INDEX] + " month(s), "
+ splitResults[YEAR_INDEX] + " year(s) [should be 31, 12, 100]");
splitResults = splitDays(146097);
System.out.println("146097 day = " + splitResults[DAY_INDEX] + " days(s), "
+ splitResults[MONTH_INDEX] + " month(s), "
+ splitResults[YEAR_INDEX] + " year(s) [should be 31, 12, 400]");
splitResults = splitDays(145811);
System.out.println("145811 day = " + splitResults[DAY_INDEX] + " days(s), "
+ splitResults[MONTH_INDEX] + " month(s), "
+ splitResults[YEAR_INDEX] + " year(s) [should be 20, 3, 400]");
splitResults = splitDays(402074);
System.out.println("402074 day = " + splitResults[DAY_INDEX] + " days(s), "
+ splitResults[MONTH_INDEX] + " month(s), "
+ splitResults[YEAR_INDEX] + " year(s) [should be 4, 11, 1101]");
splitResults = splitDays(722276);
System.out.println("722276 day = " + splitResults[DAY_INDEX] + " days(s), "
+ splitResults[MONTH_INDEX] + " month(s), "
+ splitResults[YEAR_INDEX] + " year(s) [should be 11, 7, 1978]");
splitResults = splitDays(730365);
System.out.println("730365 day = " + splitResults[DAY_INDEX] + " days(s), "
+ splitResults[MONTH_INDEX] + " month(s), "
+ splitResults[YEAR_INDEX] + " year(s) [should be 2, 9, 2000]");
splitResults = splitDays(731477);
System.out.println("731477 day = " + splitResults[DAY_INDEX] + " days(s), "
+ splitResults[MONTH_INDEX] + " month(s), "
+ splitResults[YEAR_INDEX] + " year(s) [should be 19, 9, 2003]");
// ********************** test splitHours **********************
System.out.println("\n********************** test splitHours **********************");
splitResults = splitHours(1);
System.out.println("1 hour = " + splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 1, 1, 1]");
splitResults = splitHours(729);
System.out.println("729 hours = " + splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 9, 31, 1, 1]");
splitResults = splitHours(8724);
System.out.println("8724 hours = " + splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 12, 30, 12, 1]");
splitResults = splitHours(8760);
System.out.println("8760 hours = " + splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 24, 31, 12, 1]");
splitResults = splitHours(35044);
System.out.println("35044 hours = " + splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 4, 31, 12, 4]");
splitResults = splitHours(26642);
System.out.println("26642 hours = " + splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 2, 16, 1, 4]");
splitResults = splitHours(1081);
System.out.println("1081 hours = " + splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 1, 15, 2, 1]");
splitResults = splitHours(876555);
System.out.println("876555 hours = " + splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 3, 31, 12, 100]");
splitResults = splitHours(3506308);
System.out.println("3506308 hours = " + splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 4, 31, 12, 400]");
splitResults = splitHours(9649757);
System.out.println("9649757 hours = " + splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 5, 4, 11, 1101]");
splitResults = splitHours(17334606);
System.out.println("17334606 hours = " + splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 6, 11, 7, 1978]");
splitResults = splitHours(17528743);
System.out.println("17528743 hours = " + splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 7, 2, 9, 2000]");
splitResults = splitHours(17555432);
System.out.println("17555432 hours = " + splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 8, 19, 9, 2003]");
// ********************** test splitMinutes **********************
System.out.println("\n********************** test splitMinutes **********************");
splitResults = splitMinutes(1);
System.out.println("1 minute = " + splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 1, 1, 1, 1, 1]");
splitResults = splitMinutes(43710);
System.out.println("43710 minutes = " + splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 30, 9, 31, 1, 1]");
splitResults = splitMinutes(523385);
System.out.println("523385 minutes = " + splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 5, 12, 30, 12, 1]");
splitResults = splitMinutes(525541);
System.out.println("525541 minutes = " + splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 1, 24, 31, 12, 1]");
splitResults = splitMinutes(2103840);
System.out.println("2103840 minutes = " + splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 60, 24, 31, 12, 4]");
splitResults = splitMinutes(1598506);
System.out.println("1598506 minutes = " + splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 46, 2, 16, 1, 4]");
splitResults = splitMinutes(64836);
System.out.println("64836 minutes = " + splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 36, 1, 15, 2, 1]");
splitResults = splitMinutes(52593248);
System.out.println("52593248 minutes = " + splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 8, 3, 31, 12, 100]");
splitResults = splitMinutes(210378474);
System.out.println("210378474 minutes = " + splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 54, 4, 31, 12, 400]");
splitResults = splitMinutes(578985365);
System.out.println("578985365 minutes = " + splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 5, 5, 4, 11, 1101]");
splitResults = splitMinutes(1040076321);
System.out.println("1040076321 minutes = " + splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 21, 6, 11, 7, 1978]");
splitResults = splitMinutes(1051724573);
System.out.println("1051724573 minutes = " + splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 53, 7, 2, 9, 2000]");
splitResults = splitMinutes(1053325886);
System.out.println("1053325886 minutes = " + splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 26, 8, 19, 9, 2003]");
splitResults = splitSeconds(1);
System.out.println("1 second = " + splitResults[SECOND_INDEX] + "s, "
+ splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 1, 1, 1, 1, 1, 1]");
splitResults = splitSeconds(2622570);
System.out.println("2622570 seconds = " + splitResults[SECOND_INDEX] + "s, "
+ splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 30, 30, 9, 31, 1, 1]");
splitResults = splitSeconds(31403045);
System.out.println("31403045 seconds = " + splitResults[SECOND_INDEX] + "s, "
+ splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 5, 5, 12, 30, 12, 1]");
splitResults = splitSeconds(31532401);
System.out.println("31532401 seconds = " + splitResults[SECOND_INDEX] + "s, "
+ splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 1, 1, 24, 31, 12, 1]");
splitResults = splitSeconds(126230390);
System.out.println("126230390 seconds = " + splitResults[SECOND_INDEX] + "s, "
+ splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 50, 60, 24, 31, 12, 4]");
splitResults = splitSeconds(95910346);
System.out.println("95910346 seconds = " + splitResults[SECOND_INDEX] + "s, "
+ splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 46, 46, 2, 16, 1, 4]");
splitResults = splitSeconds(3890136);
System.out.println("3890136 seconds = " + splitResults[SECOND_INDEX] + "s, "
+ splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 36, 36, 1, 15, 2, 1]");
splitResults = splitSeconds(3155594828l);
System.out.println("3155594828 seconds = " + splitResults[SECOND_INDEX] + "s, "
+ splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 8, 8, 3, 31, 12, 100]");
splitResults = splitSeconds(12622708434l);
System.out.println("12622708434 seconds = " + splitResults[SECOND_INDEX] + "s, "
+ splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 54, 54, 4, 31, 12, 400]");
splitResults = splitSeconds(34739121845l);
System.out.println("34739121845 seconds = " + splitResults[SECOND_INDEX] + "s, "
+ splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 5, 5, 5, 4, 11, 1101]");
*/
System.out.println("September 19, 2003 09:19:19 in seconds = " + sumSeconds(2003, 9, 19, 9, 19, 19)); // 63199559982
splitResults = splitSeconds(63199559982l);
System.out.println("63199559982 seconds = " + splitResults[SECOND_INDEX] + "s, "
+ splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y");
/*
splitResults = splitSeconds(62404579221l);
System.out.println("62404579221 seconds = " + splitResults[SECOND_INDEX] + "s, "
+ splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 14, 21, 6, 11, 7, 1978]");
splitResults = splitSeconds(63103474373l);
System.out.println("63103474373 seconds = " + splitResults[SECOND_INDEX] + "s, "
+ splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 31, 53, 7, 2, 9, 2000]");
splitResults = splitSeconds(63199553126l);
System.out.println("63199553126 seconds = " + splitResults[SECOND_INDEX] + "s, "
+ splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 4, 26, 8, 19, 9, 2003]");
splitResults = splitSeconds(sumSeconds(1993, 06, 30, 23, 59, 60));
System.out.println(sumSeconds(1993, 06, 30, 23, 59, 60) + " seconds = " + splitResults[SECOND_INDEX] + "s, "
+ splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y [should be 61, 60, 24, 30, 6, 1993]");
splitResults = splitSeconds(sumSeconds(2003, 9, 19, 8, 26, 4));
System.out.println("September 19, 2003 08:26:4 in seconds = " + sumSeconds(2003, 9, 19, 8, 26, 4)
+ " = " + splitResults[SECOND_INDEX] + "s, "
+ splitResults[MINUTE_INDEX] + "mi, "
+ splitResults[HOUR_INDEX] + "h, "
+ splitResults[DAY_INDEX] + "d, "
+ splitResults[MONTH_INDEX] + "m, "
+ splitResults[YEAR_INDEX] + "y");
*/
}
}