⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 bigdate.java

📁 How to get the java home dir.
💻 JAVA
📖 第 1 页 / 共 5 页
字号:
     * Year, -999,999 to +999,999, negative is BC, positive is AD, 0 is null. If I were rewriting this, I would likely
     * encode year 1 BC as 0, and convert on output. That would simplify calculation over the 1AD -1BC barrrier.
     *
     * @noinspection WeakerAccess
     */
    protected transient int yyyy = 0;
    // -------------------------- PUBLIC STATIC METHODS --------------------------

    /**
     * Returns a BigDate object initialised to today's UTC (Greenwich GMT) date, in other words the date and time in
     * Greenwich England right now without any summer time correction. It works even if Java's default Timezone is not
     * configured correctly, but it requires your system clock accurately set to UTC time. Experiment setting your
     * system date/time to various values and making sure you are getting the expected results. Note the date in the
     * created object does not keep updating every time you reference it with methods like getOrdinal or getDD. You
     * always get the date the object was created.
     *
     * @return BigDate object initialised to today, in Greenwich.
     * @see #localToday
     * @see #today
     */
    public static BigDate UTCToday()
        {
        // 86,400,000 = 1000 * 60 * 60 * 24 = milliseconds per day
        return new BigDate( ( int ) ( System.currentTimeMillis() / 86400000L ) );
        }// end UTCToday

    // p u b l i c m e t h o d s

    /**
     * calculate the age in years, months and days. To compute elapsed time between two dates, use the first as the
     * birthDate and the second as the asof.
     *
     * @param birthDate usually the birth of a person.
     * @param asof      usually today, the day you want the age as of. asof must come after birthDate to get a
     *                  meaningful result.
     * @return array of three ints (not Integers). [0]=age in years, [1]=age in months, [2]=age in days.
     * @see #localToday
     * @see #today
     * @see #UTCToday
     */
    public static int[] age( BigDate birthDate, BigDate asof )
        {
        if ( birthDate.getOrdinal() >= asof.getOrdinal() )
            {
            return new int[] { 0, 0, 0 };
            }
        int birthYYYY = birthDate.getYYYY();
        int birthMM = birthDate.getMM();
        int birthDD = birthDate.getDD();

        int asofYYYY = asof.getYYYY();
        int asofMM = asof.getMM();
        int asofDD = asof.getDD();

        int ageInYears = asofYYYY - birthYYYY;
        int ageInMonths = asofMM - birthMM;
        int ageInDays = asofDD - birthDD;

        if ( ageInDays < 0 )
            {
            // This does not need to be a while loop because
            // birthDD is always less than daysInbirthMM month.
            // Guaranteed after this single treatment, ageInDays will be >= 0.
            // i.e. ageInDays = asofDD - birthDD + daysInBirthMM.
            ageInDays += BigDate.daysInMonth( birthMM, birthYYYY );
            ageInMonths--;
            }

        if ( ageInMonths < 0 )
            {
            ageInMonths += 12;
            ageInYears--;
            }
        if ( birthYYYY < 0 && asofYYYY > 0 )
            {
            ageInYears--;
            }

        if ( ageInYears < 0 )
            {
            ageInYears = 0;
            ageInMonths = 0;
            ageInDays = 0;
            }
        int[] result = new int[3];
        result[ 0 ] = ageInYears;
        result[ 1 ] = ageInMonths;
        result[ 2 ] = ageInDays;
        return result;
        }// end age

    /**
     * Get day of week for given ordinal. It is one-based starting with Sunday.
     *
     * @param ordinal days since Jan 1, 1970 to test.
     * @return day of week 1=Sunday 2=Monday 3=Tuesday 4=Wednesday 5=Thursday 6=Friday 7=Saturday Compatible with Sun's
     *         1=Calendar.SUNDAY Not compatible with BigDate.getDayOfWeek.
     * @see #isoDayOfWeek
     * @see #dayOfWeek
     * @see #getCalendarDayOfWeek
     */
    public static int calendarDayOfWeek( int ordinal )
        {
        return dayOfWeek( ordinal ) + 1;
        }

    /**
     * Get 3-char abbreviation of a given day of the week
     *
     * @param dayOfWeek sunday = 0
     * @return abbreviation for day of week, e.g. "sun", all lower case.
     */
    public static String dayAbbr( int dayOfWeek )
        {
        return dayAbbr[ dayOfWeek ];
        }

    /**
     * Get full name of given day of the week
     *
     * @param dayOfWeek sunday = 0
     * @return name of day of week e.g. "Sunday"
     */
    public static String dayName( int dayOfWeek )
        {
        return dayName[ dayOfWeek ];
        }

    /**
     * Get day of week for given ordinal. Is it zero-based starting with Sunday.
     *
     * @param ordinal days since Jan 1, 1970 to test.
     * @return day of week 0=Sunday 1=Monday 2=Tuesday 3=Wednesday 4=Thursday 5=Friday 6=Saturday WARNING: not
     *         compatible with 1=Calendar.SUNDAY
     * @see #calendarDayOfWeek
     * @see #isoDayOfWeek
     * @see #getDayOfWeek
     */
    public static int dayOfWeek( int ordinal )
        {
        // modulus in Java is "broken" for negative numbers
        // so we adjust to make the dividend positive.
        // By "broken" I mean the official rules for what
        // is supposed to happen for negative dividends
        // won't give the desired result in this case.
        // See modulus in the Java glossary for more details.
        return ( ordinal == NULL_ORDINAL )
               ? 0
               : ( ( ordinal + SundayIsZeroAdjustment - MIN_ORDINAL ) % 7 );
        }

    /**
     * How many days are there in a given month?
     *
     * @param mm   month 1 to 12 (not 0 to 11 as in Sun's Date), no lead 0.
     * @param leap true if you are interested in a leap year
     * @return how many days are in that month
     */
    public static int daysInMonth( int mm, boolean leap )
        {
        if ( mm != 2 )
            {
            return usual_DaysPerMonthTable[ mm - 1 ];
            }
        else
            {
            return leap ? 29 : 28;
            }
        }// end daysInMonth

    /**
     * How many days are there in a given month? o
     *
     * @param mm   month 1 to 12 (not 0 to 11 as in Sun's Date), no lead 0.
     * @param yyyy year of interest.
     * @return how many days are in that month
     */
    public static int daysInMonth( int mm, int yyyy )
        {
        if ( mm != 2 )
            {
            return usual_DaysPerMonthTable[ mm - 1 ];
            }
        else
            {
            return isLeap( yyyy ) ? 29 : 28;
            }
        }// end daysInMonth

    /**
     * Multiply then divide using floored rather than the usual truncated arithmetic, using a long intermediate.
     *
     * @param multiplicand one of two numbers to multiply together
     * @param multiplier   one of two numbers to multiply together
     * @param divisor      number to divide by
     * @return (multiplicand * multiplier) / divisor
     */
    public static int flooredMulDiv( int multiplicand,
                                     int multiplier,
                                     int divisor )
        {
        long result = ( long ) multiplicand * ( long ) multiplier;
        if ( result >= 0 )
            {
            return ( int ) ( result / divisor );
            }
        else
            {
            return ( int ) ( ( result - divisor + 1 ) / divisor );
            }
        }// end flooredMulDiv

    /**
     * Embeds copyright notice
     *
     * @return copyright notice
     * @noinspection SameReturnValue
     */
    public static String getCopyright()
        {
        return "BigDate 5.1 freeware copyright (c) 1997-2008 Roedy Green, Canadian Mind Products, http://mindprod.com roedyg@mindprod.com";
        }

    /**
     * Is the given year a leap year, considering history, mod 100 and mod 400 rules? By 1582, this excess of leap years
     * had built up noticeably. At the suggestion of astronomers Luigi Lilio and Christopher Clavius, Pope Gregory XIII
     * dropped 10 days from the calendar. Thursday 1582 October 4 Julian was followed immediately by Friday 1582 October
     * 15 Gregorian. He decreed that every 100 years, a leap year should be dropped except that every 400 years the leap
     * year should be restored. Only Italy, Poland, Portugual and Spain went along with the new calendar immediately.
     * One by one other countries adopted it in different years. Britain and its territories (including the USA and
     * Canada) adopted it in 1752. By then, 11 days had to be dropped. 1752 September 2 was followed immediately by 1752
     * September 14. The Gregorian calendar is the most widely used scheme. This is the scheme endorsed by the US Naval
     * observatory. It corrects the year to 365.2425. It gets ahead 1 day every 3289 years. For BC dates, the years the
     * years 1, 5, 9 are leap years, not 4, 8, 12 as you might expect, from the general rule.
     *
     * @param yyyy year to test.
     * @return true if the year is a leap year.
     * @noinspection SimplifiableIfStatement
     */
    public static boolean isLeap( int yyyy )
        {
        // if you change this code, make sure you make corresponding changes to
        // jan01OfYear, toGregorian, MondayIsZeroAdjustment,
        // SundayIsZeroAdjustment,
        // AD_epochAdjustment and BC_epochAdjustment
        // yyyy & 3 is a fast way of saying yyyy % 4
        if ( yyyy < Leap100RuleYYYY )
            {
            if ( yyyy < 0 )
                {
                return ( ( yyyy + 1 ) & 3 ) == 0;
                }
            else
                {
                return ( yyyy & 3 ) == 0;
                }
            }
        if ( ( yyyy & 3 ) != 0 )
            {
            return false;
            }
        if ( yyyy % 100 != 0 )
            {
            return true;
            }
        if ( yyyy < Leap400RuleYYYY )
            {
            return false;
            }
        return yyyy % 400 == 0;
        }

    /**
     * Test to see if the given yyyy-mm-dd is a date as a String is legitimate. must have 4-digit years, and use dashes
     * between the number and no sign Does extensive checks considering leap years, missing days etc.
     *
     * @param yyyy_mm_dd string of form "yyyy-mm-dd".
     * @return true if that represents a valid date.
     */
    public static boolean isValid( String yyyy_mm_dd )
        {
        try
            {
            if ( yyyy_mm_dd.length() != 10 )
                {
                return false;
                }
            int yyyy = Integer.parseInt( yyyy_mm_dd.substring( 0, 4 ) );
            int mm = Integer.parseInt( yyyy_mm_dd.substring( 5, 7 ) );
            int dd = Integer.parseInt( yyyy_mm_dd.substring( 8, 10 ) );
            return BigDate.isValid( yyyy, mm, dd );
            }
        catch ( NumberFormatException e )
            {
            return false;
            }
        }

    /**
     * Test to see if the given yyyy, mm, dd date is legitimate. Does extensive checks considering leap years, missing
     * days etc.
     *
     * @param yyyy -999,999 (BC) to +999,999 (AD)
     * @param mm   month 1 to 12 (not 0 to 11 as in Sun's Date), no lead 0.
     * @param dd   day 1 to 31, no lead 0.
     * @return true if yyyy mm dd is a valid date.
     * @noinspection SimplifiableIfStatement
     */
    public static boolean isValid( int yyyy, int mm, int dd )
        {
        // null date 0000 00 00 is considered valid
        // but otherwise year 0000 never happened.
        if ( yyyy == 0 )
            {
            return ( mm == 0 ) && ( dd == 0 );
            }
        if ( ( yyyy < MIN_YEAR )
             || ( yyyy > MAX_YEAR )
             || ( mm < 1 )
             || ( mm > 12 )
             || ( dd < 1 )
             || ( dd > 31 ) )
            {
            return false;
            }
        // account for missing 10 days in 1582.
        // Thursday 1582 October 4 Julian was followed
        // immediately by Friday 1582 October 15
        // Similarly for the British Calendar
        if ( yyyy == OJC_lastYYYY
             && mm == OJC_lastMM
             && OJC_lastDD < dd
             && dd < GC_firstDD )
            {
            return false;
            }
        return dd <= daysInMonth( mm, yyyy );
        }// end isValid

    /**
     * Get day of week 1 to 7 for this ordinal according to the ISO standard IS-8601. It is one-based starting with
     * Monday.
     *
     * @param ordinal days since Jan 1, 1970 to test.
     * @return day of week 1=Monday to 7=Sunday, 0 for null date. WARNING: not compatible with 1=Calendar.SUNDAY.
     * @see BigDate#dayOfWeek(int)
     */
    public static int isoDayOfWeek( int ordinal )
        {
        // modulus in Java is "broken" for negative numbers
        // so we adjust to make the dividend positive.
        // By "broken" I mean the official rules for what
        // is supposed to happen for negative dividends
        // won't give the desired result in this case.
        // See modulus in the Java glossary for more details.
        return ( ordinal == NULL_ORDINAL )
               ? 0
               : ( ( ordinal + MondayIsZeroAdjustment - MIN_ORDINAL ) % 7 ) + 1;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -