/*------------------------------------------------------------------------------------- * Copyright: R.S.J. Koster 2001 * * Changes: * Ver. Date Name Searchcode Reason * 1.0 2001-10-01 R. Koster - Initial coding. * *------------------------------------------------------------------------------------- */ import java.util.Calendar; import java.util.GregorianCalendar; /** * Calculates the Julian date for a given date-time. * * @see "Documentation on java.util.GregorianCalendar" * @see Julian Dates * * @version 1.0 * @author  R. Koster */ public class JulianDate { /** * Validates a given date. * * @return true if valid, else false. */ private static boolean isValidDate( int y, int m, int d ) { boolean valid = true; if (y < 1) {valid = false;} if ( (m < 1) || (m > 12) ) {valid = false;} if ( (d < 1) || (d > 31) ) {valid = false;} if ( (m == 4) || (m == 6) || (m == 9) || (m == 11) ) { if (d > 30) {valid = false;} } if (m == 2) { GregorianCalendar calendar = new GregorianCalendar(y, m - 1, d); // NB. See NB on month numbering method main. if ( calendar.isLeapYear(y) ) { if (d > 29) {valid = false;} } else { if (d > 28) {valid = false;} } } return valid; } /** * Validates a given time. * * @return true if valid, else false. */ private static boolean isValidTime( int h, int m, int s ) { if ((h < 0) || (h > 23)) {return false;} if ((m < 0) || (m > 59)) {return false;} if ((s < 0) || (s > 59)) {return false;} return true; } /** * Main loop. * * @param args optional date, time and era strings. When ran without arguments the syntax is displayed. */ public static void main( String[] args ) { if (args.length == 0) { System.out.println( "JulianDate version 1.0" ); System.out.println( "Usage: java JulianDate yyyy-mm-dd [hh:mm:ss [a|b]]" ); System.out.println(); System.out.println( "With a = AD and b = BC (era).\n" + "Defaults: 12:00:00 a\n" + "NB. Time entered is assumed to be UT (Universal Time).\n" + "\n" + "JulianDate is based on java.util.GregorianCalendar. For more information on calendars \n" + "and Julian Dates see the documentation on that class.\n" + "Also see http://aa.usno.navy.mil/data/docs/JulianDate.html" ); } else { // Get date from arguments. int y = 0; int m = 0; int d = 0; boolean invalidDate = false; try { y = Integer.parseInt( args[0].substring(0, 4) ); m = Integer.parseInt( args[0].substring(5, 7) ); d = Integer.parseInt( args[0].substring(8, 10) ); } catch (Exception e) {invalidDate = true;} if ( !isValidDate(y, m, d) ) {invalidDate = true;} if (invalidDate) {System.out.println("Invalid date.");} // Get time from arguments. int h = 12; int min = 0; int s = 0; boolean invalidTime = false; if (args.length > 1) { try { h = Integer.parseInt( args[1].substring(0, 2) ); min = Integer.parseInt( args[1].substring(3, 5) ); s = Integer.parseInt( args[1].substring(6, 8) ); } catch (Exception e) {invalidTime = true;} if ( !isValidTime(h, min, s) ) {invalidTime = true;} if (invalidTime) {System.out.println("Invalid time.");} } // Get era from arguments. boolean ad = true; boolean invalidEra = false; if (args.length == 3) { if ( args[2].equals("a") ) {ad = true;} else { if ( args[2].equals("b") ) {ad = false;} else { invalidEra = true; System.out.println("Invalid era."); }; } } if (!invalidDate && !invalidTime && !invalidEra) { // Calculate user date milliseconds. // NB. GregorianCalendar numbers the months jan = 0, feb = 1, ... Which is unhandy. Calendar calendar = new GregorianCalendar( y, m - 1, d, h, min, s ); if (!ad) {calendar.set( Calendar.ERA, GregorianCalendar.BC );} long t1 = calendar.getTime().getTime(); // Convert to the UT time the user meant. t1 = t1 + calendar.get(Calendar.ZONE_OFFSET) + calendar.get(Calendar.DST_OFFSET); // Calculate epoch date milliseconds. calendar.set( Calendar.ERA, GregorianCalendar.BC ); calendar.set( Calendar.YEAR, 4713 ); calendar.set( Calendar.MONTH, 0 ); calendar.set( Calendar.DAY_OF_MONTH, 1 ); calendar.set( Calendar.HOUR_OF_DAY, 12 ); calendar.set( Calendar.MINUTE, 0 ); calendar.set( Calendar.SECOND, 0 ); long t0 = calendar.getTime().getTime(); // Convert to the UT time. t0 = t0 + calendar.get(Calendar.ZONE_OFFSET) + calendar.get(Calendar.DST_OFFSET); // Finally calculate Julian date. long deltaT = t1 - t0; double delta = deltaT; delta = delta / (1000 * 60 * 60 * 24); System.out.println( "Julian date = " + delta ); } } } }