2 *******************************************************************************
\r
3 * Copyright (C) 2004-2006, International Business Machines Corporation and *
\r
4 * others. All Rights Reserved. *
\r
5 *******************************************************************************
\r
9 package com.ibm.icu.dev.test.timescale;
\r
11 import java.util.Date;
\r
12 import java.util.Locale;
\r
13 import com.ibm.icu.util.GregorianCalendar;
\r
14 import com.ibm.icu.util.SimpleTimeZone;
\r
15 import com.ibm.icu.util.TimeZone;
\r
16 import com.ibm.icu.util.UniversalTimeScale;
\r
17 import com.ibm.icu.dev.test.TestFmwk;
\r
22 * TODO To change the template for this generated type comment go to
\r
23 * Window - Preferences - Java - Code Style - Code Templates
\r
25 public class TimeScaleDataTest extends TestFmwk
\r
29 * Default contstructor.
\r
31 public TimeScaleDataTest()
\r
35 private void roundTripTest(long value, int scale)
\r
37 long rt = UniversalTimeScale.toLong(UniversalTimeScale.from(value, scale), scale);
\r
40 errln("Round-trip error: time scale = " + scale + ", value = " + value + ", round-trip = " + rt);
\r
44 private void toLimitTest(long toLimit, long fromLimit, int scale)
\r
46 long result = UniversalTimeScale.toLong(toLimit, scale);
\r
48 if (result != fromLimit) {
\r
49 errln("toLimit failure: scale = " + scale + ", toLimit = " + toLimit +
\r
50 ", toLong(toLimit, scale) = " + result + ", fromLimit = " + fromLimit);
\r
54 private void epochOffsetTest(long epochOffset, long units, int scale)
\r
56 long universalEpoch = epochOffset * units;
\r
57 long local = UniversalTimeScale.toLong(universalEpoch, scale);
\r
60 errln("toLong(epochOffset, scale): scale = " + scale + ", epochOffset = " + universalEpoch +
\r
61 ", result = " + local);
\r
64 local = UniversalTimeScale.toLong(0, scale);
\r
66 if (local != -epochOffset) {
\r
67 errln("toLong(0, scale): scale = " + scale + ", result = " + local);
\r
70 long universal = UniversalTimeScale.from(-epochOffset, scale);
\r
72 if (universal != 0) {
\r
73 errln("from(-epochOffest, scale): scale = " + scale + ", epochOffset = " + epochOffset +
\r
74 ", result = " + universal);
\r
77 universal = UniversalTimeScale.from(0, scale);
\r
79 if (universal != universalEpoch) {
\r
80 errln("from(0, scale): scale = " + scale + ", result = " + universal);
\r
84 public void TestEpochOffsets()
\r
86 for (int scale = 0; scale < UniversalTimeScale.MAX_SCALE; scale += 1) {
\r
87 long units = UniversalTimeScale.getTimeScaleValue(scale, UniversalTimeScale.UNITS_VALUE);
\r
88 long epochOffset = UniversalTimeScale.getTimeScaleValue(scale, UniversalTimeScale.EPOCH_OFFSET_VALUE);
\r
90 epochOffsetTest(epochOffset, units, scale);
\r
94 public void TestFromLimits()
\r
96 for (int scale = 0; scale < UniversalTimeScale.MAX_SCALE; scale += 1) {
\r
97 long fromMin = UniversalTimeScale.getTimeScaleValue(scale, UniversalTimeScale.FROM_MIN_VALUE);
\r
98 long fromMax = UniversalTimeScale.getTimeScaleValue(scale, UniversalTimeScale.FROM_MAX_VALUE);
\r
100 roundTripTest(fromMin, scale);
\r
101 roundTripTest(fromMax, scale);
\r
105 public void TestToLimits()
\r
107 for (int scale = 0; scale < UniversalTimeScale.MAX_SCALE; scale += 1) {
\r
108 long fromMin = UniversalTimeScale.getTimeScaleValue(scale, UniversalTimeScale.FROM_MIN_VALUE);
\r
109 long fromMax = UniversalTimeScale.getTimeScaleValue(scale, UniversalTimeScale.FROM_MAX_VALUE);
\r
110 long toMin = UniversalTimeScale.getTimeScaleValue(scale, UniversalTimeScale.TO_MIN_VALUE);
\r
111 long toMax = UniversalTimeScale.getTimeScaleValue(scale, UniversalTimeScale.TO_MAX_VALUE);
\r
113 toLimitTest(toMin, fromMin, scale);
\r
114 toLimitTest(toMax, fromMax, scale);
\r
118 // Test with data from .Net System.DateTime ---------------------------- ***
\r
121 * This data was generated by C++.Net code like
\r
122 * Console::WriteLine(L" {{ {0}, 1, 1, INT64_C({1}) }},", year, DateTime(year, 1, 1).Ticks);
\r
123 * with the DateTime constructor taking int values for year, month, and date.
\r
125 static private final long dotNetDateTimeTicks[] = {
\r
126 /* year, month, day, ticks */
\r
127 100, 1, 1, 31241376000000000L,
\r
128 100, 3, 1, 31292352000000000L,
\r
129 200, 1, 1, 62798112000000000L,
\r
130 200, 3, 1, 62849088000000000L,
\r
131 300, 1, 1, 94354848000000000L,
\r
132 300, 3, 1, 94405824000000000L,
\r
133 400, 1, 1, 125911584000000000L,
\r
134 400, 3, 1, 125963424000000000L,
\r
135 500, 1, 1, 157469184000000000L,
\r
136 500, 3, 1, 157520160000000000L,
\r
137 600, 1, 1, 189025920000000000L,
\r
138 600, 3, 1, 189076896000000000L,
\r
139 700, 1, 1, 220582656000000000L,
\r
140 700, 3, 1, 220633632000000000L,
\r
141 800, 1, 1, 252139392000000000L,
\r
142 800, 3, 1, 252191232000000000L,
\r
143 900, 1, 1, 283696992000000000L,
\r
144 900, 3, 1, 283747968000000000L,
\r
145 1000, 1, 1, 315253728000000000L,
\r
146 1000, 3, 1, 315304704000000000L,
\r
147 1100, 1, 1, 346810464000000000L,
\r
148 1100, 3, 1, 346861440000000000L,
\r
149 1200, 1, 1, 378367200000000000L,
\r
150 1200, 3, 1, 378419040000000000L,
\r
151 1300, 1, 1, 409924800000000000L,
\r
152 1300, 3, 1, 409975776000000000L,
\r
153 1400, 1, 1, 441481536000000000L,
\r
154 1400, 3, 1, 441532512000000000L,
\r
155 1500, 1, 1, 473038272000000000L,
\r
156 1500, 3, 1, 473089248000000000L,
\r
157 1600, 1, 1, 504595008000000000L,
\r
158 1600, 3, 1, 504646848000000000L,
\r
159 1700, 1, 1, 536152608000000000L,
\r
160 1700, 3, 1, 536203584000000000L,
\r
161 1800, 1, 1, 567709344000000000L,
\r
162 1800, 3, 1, 567760320000000000L,
\r
163 1900, 1, 1, 599266080000000000L,
\r
164 1900, 3, 1, 599317056000000000L,
\r
165 2000, 1, 1, 630822816000000000L,
\r
166 2000, 3, 1, 630874656000000000L,
\r
167 2100, 1, 1, 662380416000000000L,
\r
168 2100, 3, 1, 662431392000000000L,
\r
169 2200, 1, 1, 693937152000000000L,
\r
170 2200, 3, 1, 693988128000000000L,
\r
171 2300, 1, 1, 725493888000000000L,
\r
172 2300, 3, 1, 725544864000000000L,
\r
173 2400, 1, 1, 757050624000000000L,
\r
174 2400, 3, 1, 757102464000000000L,
\r
175 2500, 1, 1, 788608224000000000L,
\r
176 2500, 3, 1, 788659200000000000L,
\r
177 2600, 1, 1, 820164960000000000L,
\r
178 2600, 3, 1, 820215936000000000L,
\r
179 2700, 1, 1, 851721696000000000L,
\r
180 2700, 3, 1, 851772672000000000L,
\r
181 2800, 1, 1, 883278432000000000L,
\r
182 2800, 3, 1, 883330272000000000L,
\r
183 2900, 1, 1, 914836032000000000L,
\r
184 2900, 3, 1, 914887008000000000L,
\r
185 3000, 1, 1, 946392768000000000L,
\r
186 3000, 3, 1, 946443744000000000L,
\r
188 1601, 1, 1, 504911232000000000L,
\r
189 1899, 12, 31, 599265216000000000L,
\r
190 1904, 1, 1, 600527520000000000L,
\r
191 1970, 1, 1, 621355968000000000L,
\r
192 2001, 1, 1, 631139040000000000L,
\r
193 9900, 3, 1, 3123873216000000000L,
\r
194 9999, 12, 31, 3155378112000000000L
\r
198 * ICU's Universal Time Scale is designed to be tick-for-tick compatible with
\r
199 * .Net System.DateTime. Verify that this is so for the
\r
200 * .Net-supported date range (years 1-9999 AD).
\r
201 * This requires a proleptic Gregorian calendar because that's what .Net uses.
\r
202 * Proleptic: No Julian/Gregorian switchover, or a switchover before
\r
203 * any date that we test, that is, before 0001 AD.
\r
205 public void TestDotNet() {
\r
207 final long dayMillis = 86400 * 1000L; /* 1 day = 86400 seconds */
\r
208 final long dayTicks = 86400 * 10000000L;
\r
209 final int kYear = 0; // offset for dotNetDateTimeTicks[] field
\r
210 final int kMonth = 1;
\r
211 final int kDay = 2;
\r
212 final int kTicks = 3;
\r
213 final int kIncrement = 4;
\r
214 GregorianCalendar cal;
\r
216 long ticks, millis;
\r
219 /* Open a proleptic Gregorian calendar. */
\r
220 long before0001AD = -1000000 * dayMillis;
\r
221 utc = new SimpleTimeZone(0, "UTC");
\r
222 cal = new GregorianCalendar(utc, Locale.ENGLISH);
\r
223 cal.setGregorianChange(new Date(before0001AD));
\r
224 for(i = 0; i < dotNetDateTimeTicks.length; i += kIncrement) {
\r
225 /* Test conversion from .Net/Universal time to ICU time. */
\r
226 millis = UniversalTimeScale.toLong(dotNetDateTimeTicks[i + kTicks], UniversalTimeScale.ICU4C_TIME);
\r
228 cal.set((int)dotNetDateTimeTicks[i + kYear],
\r
229 (int)dotNetDateTimeTicks[i + kMonth] - 1, /* Java & ICU use January = month 0. */
\r
230 (int)dotNetDateTimeTicks[i + kDay]);
\r
231 icuDate = cal.getTimeInMillis();
\r
232 if(millis != icuDate) {
\r
233 /* Print days not millis. */
\r
234 errln("UniversalTimeScale.toLong(ticks[" + i + "], ICU4C)=" +
\r
235 (millis/dayMillis) + " != " + (icuDate/dayMillis) +
\r
236 "=ucal_getMillis(" + dotNetDateTimeTicks[i + kYear] +
\r
237 "-" + dotNetDateTimeTicks[i + kMonth] +
\r
238 "-" + dotNetDateTimeTicks[i + kDay] + ")");
\r
241 /* Test conversion from ICU time to .Net/Universal time. */
\r
242 ticks = UniversalTimeScale.from(icuDate, UniversalTimeScale.ICU4C_TIME);
\r
243 if(ticks != dotNetDateTimeTicks[i + kTicks]) {
\r
244 /* Print days not ticks. */
\r
245 errln("UniversalTimeScale.from(date[" + i + "], ICU4C)=" +
\r
246 (ticks/dayTicks) + " != " + dotNetDateTimeTicks[i + kTicks]/dayTicks +
\r
247 "=.Net System.DateTime(" + dotNetDateTimeTicks[i + kYear] +
\r
248 "-" + dotNetDateTimeTicks[i + kMonth] +
\r
249 "-" + dotNetDateTimeTicks[i + kDay] + ").Ticks");
\r
254 public static void main(String[] args)
\r
256 new TimeScaleDataTest().run(args);
\r