001: /*
002: *******************************************************************************
003: * Copyright (C) 1996-2004, International Business Machines Corporation and *
004: * others. All Rights Reserved. *
005: *******************************************************************************
006: *
007: */
008:
009: package com.ibm.icu.dev.tool.timescale;
010:
011: import java.util.Locale;
012:
013: import com.ibm.icu.math.BigDecimal;
014: import com.ibm.icu.text.MessageFormat;
015: import com.ibm.icu.util.Calendar;
016: import com.ibm.icu.util.SimpleTimeZone;
017: import com.ibm.icu.util.TimeZone;
018: import com.ibm.icu.util.UniversalTimeScale;
019:
020: /**
021: * This class calculates the minimum and maximum values which can be
022: * used as arguments to <code>toLong</code> and <code>from</code>.
023: *
024: * NOTE: If you change the way in which these values are calculated, it
025: * may be necessary to disable to <code>toRangeCheck()</code> and
026: * <code>fromRangeCheck()</code> methods in the <code>UniversalTimeScale</code>
027: * for all of the calculations to run without throwing an error.
028: *
029: * @see com.ibm.icu.util.UniversalTimeScale
030: *
031: * @draft ICU 3.2
032: */
033: public class CalculateLimits {
034:
035: /**
036: * The default constructor.
037: *
038: * @draft ICU 3.2
039: */
040: public CalculateLimits() {
041: }
042:
043: /**
044: * This method first calculates the <code>from</code> limits by
045: * passing <code>Long.MIN_VALUE</code> and <code>Long.MAX_VALUE</code> to
046: * the (internal) <code>toBigDecimalTrunc()</code> method. Any values outside
047: * of the range of a <code>long</code> are pinned.
048: *
049: * The mimimum and maximum values for <code>toLong</code> are calulated by passing
050: * the min and max values calculated above to <code>BigDecimalFrom()</code>. Because
051: * this method will round, the returned values are adjusted to take this into account.
052: *
053: * @see com.ibm.icu.util.UniversalTimeScale
054: *
055: * @param args - the command line arugments
056: *
057: * @draft ICU 3.2
058: */
059: public static void main(String[] args) {
060: TimeZone utc = new SimpleTimeZone(0, "UTC");
061: Calendar cal = Calendar.getInstance(utc, Locale.ENGLISH);
062: MessageFormat fmt = new MessageFormat("{0}L, {1}L, {2}L, {3}L");
063: BigDecimal universalMin = new BigDecimal(Long.MIN_VALUE);
064: BigDecimal universalMax = new BigDecimal(Long.MAX_VALUE);
065: Object limitArgs[] = { null, null, null, null };
066:
067: System.out.println("\nTo, From limits:");
068:
069: // from limits
070: for (int scale = 0; scale < UniversalTimeScale.MAX_SCALE; scale += 1) {
071: BigDecimal min = UniversalTimeScale.toBigDecimalTrunc(
072: universalMin, scale).max(universalMin);
073: BigDecimal max = UniversalTimeScale.toBigDecimalTrunc(
074: universalMax, scale).min(universalMax);
075: long minLong = min.longValue();
076: long maxLong = max.longValue();
077:
078: limitArgs[2] = min.toString();
079: limitArgs[3] = max.toString();
080:
081: // to limits
082: BigDecimal minTrunc = UniversalTimeScale.bigDecimalFrom(
083: min, scale);
084: BigDecimal maxTrunc = UniversalTimeScale.bigDecimalFrom(
085: max, scale);
086: BigDecimal minResidue = minTrunc.subtract(universalMin);
087: BigDecimal maxResidue = universalMax.subtract(maxTrunc);
088: long units = UniversalTimeScale.getTimeScaleValue(scale,
089: UniversalTimeScale.UNITS_VALUE);
090: BigDecimal half = new BigDecimal(units == 1 ? 0
091: : units / 2 - 1);
092:
093: min = minTrunc.subtract(minResidue.min(half));
094: max = maxTrunc.add(maxResidue.min(half));
095: limitArgs[0] = min.toString();
096: limitArgs[1] = max.toString();
097:
098: System.out.println(fmt.format(limitArgs));
099:
100: // round-trip test the from limits
101: if (UniversalTimeScale.toLong(UniversalTimeScale.from(
102: minLong, scale), scale) != minLong) {
103: System.out.println("OOPS: min didn't round trip!");
104: }
105:
106: if (UniversalTimeScale.toLong(UniversalTimeScale.from(
107: maxLong, scale), scale) != maxLong) {
108: System.out.println("OOPS: max didn't round trip!");
109: }
110:
111: // make sure that the to limits convert to the from limits
112: if (UniversalTimeScale.toLong(min.longValue(), scale) != minLong) {
113: System.out.println("OOPS: toLong(toMin) != fromMin");
114: }
115:
116: if (UniversalTimeScale.toLong(max.longValue(), scale) != maxLong) {
117: System.out.println("OOPS: toLong(toMax) != fromMax");
118: }
119: }
120: }
121: }
|