Team Ai
Datasetpublic

codekingpro/portable-devtools

sourceHugging Faceupdated 5mo agoView on Hugging Face
1likes16kdownloads
utmscale.h491 linesDownload Raw Back to unicode
1// © 2016 and later: Unicode, Inc. and others.
2// License & terms of use: http://www.unicode.org/copyright.html
3/*
4*******************************************************************************
5* Copyright (C) 2004 - 2008, International Business Machines Corporation and
6* others. All Rights Reserved.
7*******************************************************************************
8*/
9
10#ifndef UTMSCALE_H
11#define UTMSCALE_H
12
13#include "unicode/utypes.h"
14
15#if !UCONFIG_NO_FORMATTING
16
17/** 
18 * \file
19 * \brief C API: Universal Time Scale
20 *
21 * There are quite a few different conventions for binary datetime, depending on different
22 * platforms and protocols. Some of these have severe drawbacks. For example, people using
23 * Unix time (seconds since Jan 1, 1970) think that they are safe until near the year 2038.
24 * But cases can and do arise where arithmetic manipulations causes serious problems. Consider
25 * the computation of the average of two datetimes, for example: if one calculates them with
26 * <code>averageTime = (time1 + time2)/2</code>, there will be overflow even with dates
27 * around the present. Moreover, even if these problems don't occur, there is the issue of
28 * conversion back and forth between different systems.
29 *
30 * <p>
31 * Binary datetimes differ in a number of ways: the datatype, the unit,
32 * and the epoch (origin). We'll refer to these as time scales. For example:
33 *
34 * <table border="1" cellspacing="0" cellpadding="4">
35 *  <caption>Table 1: Binary Time Scales</caption>
36 *  <tr>
37 *    <th align="left">Source</th>
38 *    <th align="left">Datatype</th>
39 *    <th align="left">Unit</th>
40 *    <th align="left">Epoch</th>
41 *  </tr>
42 *
43 *  <tr>
44 *    <td>UDTS_JAVA_TIME</td>
45 *    <td>int64_t</td>
46 *    <td>milliseconds</td>
47 *    <td>Jan 1, 1970</td>
48 *  </tr>
49 *  <tr>
50 *
51 *    <td>UDTS_UNIX_TIME</td>
52 *    <td>int32_t or int64_t</td>
53 *    <td>seconds</td>
54 *    <td>Jan 1, 1970</td>
55 *  </tr>
56 *  <tr>
57 *    <td>UDTS_ICU4C_TIME</td>
58 *
59 *    <td>double</td>
60 *    <td>milliseconds</td>
61 *    <td>Jan 1, 1970</td>
62 *  </tr>
63 *  <tr>
64 *    <td>UDTS_WINDOWS_FILE_TIME</td>
65 *    <td>int64_t</td>
66 *
67 *    <td>ticks (100 nanoseconds)</td>
68 *    <td>Jan 1, 1601</td>
69 *  </tr>
70 *  <tr>
71 *    <td>UDTS_DOTNET_DATE_TIME</td>
72 *    <td>int64_t</td>
73 *    <td>ticks (100 nanoseconds)</td>
74 *
75 *    <td>Jan 1, 0001</td>
76 *  </tr>
77 *  <tr>
78 *    <td>UDTS_MAC_OLD_TIME</td>
79 *    <td>int32_t or int64_t</td>
80 *    <td>seconds</td>
81 *    <td>Jan 1, 1904</td>
82 *
83 *  </tr>
84 *  <tr>
85 *    <td>UDTS_MAC_TIME</td>
86 *    <td>double</td>
87 *    <td>seconds</td>
88 *    <td>Jan 1, 2001</td>
89 *  </tr>
90 *
91 *  <tr>
92 *    <td>UDTS_EXCEL_TIME</td>
93 *    <td>?</td>
94 *    <td>days</td>
95 *    <td>Dec 31, 1899</td>
96 *  </tr>
97 *  <tr>
98 *
99 *    <td>UDTS_DB2_TIME</td>
100 *    <td>?</td>
101 *    <td>days</td>
102 *    <td>Dec 31, 1899</td>
103 *  </tr>
104 *
105 *  <tr>
106 *    <td>UDTS_UNIX_MICROSECONDS_TIME</td>
107 *    <td>int64_t</td>
108 *    <td>microseconds</td>
109 *    <td>Jan 1, 1970</td>
110 *  </tr>
111 * </table>
112 *
113 * <p>
114 * All of the epochs start at 00:00 am (the earliest possible time on the day in question),
115 * and are assumed to be UTC.
116 *
117 * <p>
118 * The ranges for different datatypes are given in the following table (all values in years).
119 * The range of years includes the entire range expressible with positive and negative
120 * values of the datatype. The range of years for double is the range that would be allowed
121 * without losing precision to the corresponding unit.
122 *
123 * <table border="1" cellspacing="0" cellpadding="4">
124 *  <tr>
125 *    <th align="left">Units</th>
126 *    <th align="left">int64_t</th>
127 *    <th align="left">double</th>
128 *    <th align="left">int32_t</th>
129 *  </tr>
130 *
131 *  <tr>
132 *    <td>1 sec</td>
133 *    <td align="right">5.84542x10<sup>11</sup></td>
134 *    <td align="right">285,420,920.94</td>
135 *    <td align="right">136.10</td>
136 *  </tr>
137 *  <tr>
138 *
139 *    <td>1 millisecond</td>
140 *    <td align="right">584,542,046.09</td>
141 *    <td align="right">285,420.92</td>
142 *    <td align="right">0.14</td>
143 *  </tr>
144 *  <tr>
145 *    <td>1 microsecond</td>
146 *
147 *    <td align="right">584,542.05</td>
148 *    <td align="right">285.42</td>
149 *    <td align="right">0.00</td>
150 *  </tr>
151 *  <tr>
152 *    <td>100 nanoseconds (tick)</td>
153 *    <td align="right">58,454.20</td>
154 *    <td align="right">28.54</td>
155 *    <td align="right">0.00</td>
156 *  </tr>
157 *  <tr>
158 *    <td>1 nanosecond</td>
159 *    <td align="right">584.5420461</td>
160 *    <td align="right">0.2854</td>
161 *    <td align="right">0.00</td>
162 *  </tr>
163 * </table>
164 *
165 * <p>
166 * These functions implement a universal time scale which can be used as a 'pivot',
167 * and provide conversion functions to and from all other major time scales.
168 * This datetimes to be converted to the pivot time, safely manipulated,
169 * and converted back to any other datetime time scale.
170 *
171 *<p>
172 * So what to use for this pivot? Java time has plenty of range, but cannot represent
173 * .NET <code>System.DateTime</code> values without severe loss of precision. ICU4C time addresses this by using a
174 * <code>double</code> that is otherwise equivalent to the Java time. However, there are disadvantages
175 * with <code>doubles</code>. They provide for much more graceful degradation in arithmetic operations.
176 * But they only have 53 bits of accuracy, which means that they will lose precision when
177 * converting back and forth to ticks. What would really be nice would be a
178 * <code>long double</code> (80 bits -- 64 bit mantissa), but that is not supported on most systems.
179 *
180 *<p>
181 * The Unix extended time uses a structure with two components: time in seconds and a
182 * fractional field (microseconds). However, this is clumsy, slow, and
183 * prone to error (you always have to keep track of overflow and underflow in the
184 * fractional field). <code>BigDecimal</code> would allow for arbitrary precision and arbitrary range,
185 * but we do not want to use this as the normal type, because it is slow and does not
186 * have a fixed size.
187 *
188 *<p>
189 * Because of these issues, we ended up concluding that the .NET framework's
190 * <code>System.DateTime</code> would be the best pivot. However, we use the full range
191 * allowed by the datatype, allowing for datetimes back to 29,000 BC and up to 29,000 AD.
192 * This time scale is very fine grained, does not lose precision, and covers a range that
193 * will meet almost all requirements. It will not handle the range that Java times do,
194 * but frankly, being able to handle dates before 29,000 BC or after 29,000 AD is of very limited interest.
195 *
196 */
197
198/**
199 * <code>UDateTimeScale</code> values are used to specify the time scale used for
200 * conversion into or out if the universal time scale.
201 *
202 * @stable ICU 3.2
203 */
204typedef enum UDateTimeScale {
205    /**
206     * Used in the JDK. Data is a Java <code>long</code> (<code>int64_t</code>). Value
207     * is milliseconds since January 1, 1970.
208     *
209     * @stable ICU 3.2
210     */
211    UDTS_JAVA_TIME = 0,
212
213    /**
214     * Used on Unix systems. Data is <code>int32_t</code> or <code>int64_t</code>. Value
215     * is seconds since January 1, 1970.
216     *
217     * @stable ICU 3.2
218     */
219    UDTS_UNIX_TIME,
220    
221    /**
222     * Used in IUC4C. Data is a <code>double</code>. Value
223     * is milliseconds since January 1, 1970.
224     *
225     * @stable ICU 3.2
226     */
227    UDTS_ICU4C_TIME,
228    
229    /**
230     * Used in Windows for file times. Data is an <code>int64_t</code>. Value
231     * is ticks (1 tick == 100 nanoseconds) since January 1, 1601.
232     *
233     * @stable ICU 3.2
234     */
235    UDTS_WINDOWS_FILE_TIME,
236    
237    /**
238     * Used in the .NET framework's <code>System.DateTime</code> structure. Data is an <code>int64_t</code>. Value
239     * is ticks (1 tick == 100 nanoseconds) since January 1, 0001.
240     *
241     * @stable ICU 3.2
242     */
243    UDTS_DOTNET_DATE_TIME,
244    
245    /**
246     * Used in older Macintosh systems. Data is <code>int32_t</code> or <code>int64_t</code>. Value
247     * is seconds since January 1, 1904.
248     *
249     * @stable ICU 3.2
250     */
251    UDTS_MAC_OLD_TIME,
252    
253    /**
254     * Used in newer Macintosh systems. Data is a <code>double</code>. Value
255     * is seconds since January 1, 2001.
256     *
257     * @stable ICU 3.2
258     */
259    UDTS_MAC_TIME,
260    
261    /**
262     * Used in Excel. Data is an <code>?unknown?</code>. Value
263     * is days since December 31, 1899.
264     *
265     * @stable ICU 3.2
266     */
267    UDTS_EXCEL_TIME,
268    
269    /**
270     * Used in DB2. Data is an <code>?unknown?</code>. Value
271     * is days since December 31, 1899.
272     *
273     * @stable ICU 3.2
274     */
275    UDTS_DB2_TIME,
276
277    /**
278     * Data is a <code>long</code>. Value is microseconds since January 1, 1970.
279     * Similar to Unix time (linear value from 1970) and struct timeval
280     * (microseconds resolution).
281     *
282     * @stable ICU 3.8
283     */
284    UDTS_UNIX_MICROSECONDS_TIME,
285
286#ifndef U_HIDE_DEPRECATED_API
287    /**
288     * The first unused time scale value. The limit of this enum
289     * @deprecated ICU 59 The numeric value may change over time, see ICU ticket #12420.
290     */
291    UDTS_MAX_SCALE
292#endif  /* U_HIDE_DEPRECATED_API */
293
294} UDateTimeScale;
295
296/**
297 * <code>UTimeScaleValue</code> values are used to specify the time scale values
298 * to <code>utmscale_getTimeScaleValue</code>.
299 *
300 * @see utmscale_getTimeScaleValue
301 *
302 * @stable ICU 3.2
303 */
304typedef enum UTimeScaleValue {
305    /**
306     * The constant used to select the units vale
307     * for a time scale.
308     * 
309     * @see utmscale_getTimeScaleValue
310     *
311     * @stable ICU 3.2
312     */
313    UTSV_UNITS_VALUE = 0,
314
315    /**
316     * The constant used to select the epoch offset value
317     * for a time scale.
318     * 
319     * @see utmscale_getTimeScaleValue
320     *
321     * @stable ICU 3.2
322     */
323    UTSV_EPOCH_OFFSET_VALUE=1,
324
325    /**
326     * The constant used to select the minimum from value
327     * for a time scale.
328     * 
329     * @see utmscale_getTimeScaleValue
330     *
331     * @stable ICU 3.2
332     */
333    UTSV_FROM_MIN_VALUE=2,
334
335    /**
336     * The constant used to select the maximum from value
337     * for a time scale.
338     * 
339     * @see utmscale_getTimeScaleValue
340     *
341     * @stable ICU 3.2
342     */
343    UTSV_FROM_MAX_VALUE=3,
344
345    /**
346     * The constant used to select the minimum to value
347     * for a time scale.
348     * 
349     * @see utmscale_getTimeScaleValue
350     *
351     * @stable ICU 3.2
352     */
353    UTSV_TO_MIN_VALUE=4,
354
355    /**
356     * The constant used to select the maximum to value
357     * for a time scale.
358     * 
359     * @see utmscale_getTimeScaleValue
360     *
361     * @stable ICU 3.2
362     */
363    UTSV_TO_MAX_VALUE=5,
364
365#ifndef U_HIDE_INTERNAL_API
366    /**
367     * The constant used to select the epoch plus one value
368     * for a time scale.
369     * 
370     * NOTE: This is an internal value. DO NOT USE IT. May not
371     * actually be equal to the epoch offset value plus one.
372     * 
373     * @see utmscale_getTimeScaleValue
374     *
375     * @internal ICU 3.2
376     */
377    UTSV_EPOCH_OFFSET_PLUS_1_VALUE=6,
378
379    /**
380     * The constant used to select the epoch plus one value
381     * for a time scale.
382     * 
383     * NOTE: This is an internal value. DO NOT USE IT. May not
384     * actually be equal to the epoch offset value plus one.
385     * 
386     * @see utmscale_getTimeScaleValue
387     *
388     * @internal ICU 3.2
389     */
390    UTSV_EPOCH_OFFSET_MINUS_1_VALUE=7,
391
392    /**
393     * The constant used to select the units round value
394     * for a time scale.
395     * 
396     * NOTE: This is an internal value. DO NOT USE IT.
397     * 
398     * @see utmscale_getTimeScaleValue
399     *
400     * @internal ICU 3.2
401     */
402    UTSV_UNITS_ROUND_VALUE=8,
403
404    /**
405     * The constant used to select the minimum safe rounding value
406     * for a time scale.
407     * 
408     * NOTE: This is an internal value. DO NOT USE IT.
409     * 
410     * @see utmscale_getTimeScaleValue
411     *
412     * @internal ICU 3.2
413     */
414    UTSV_MIN_ROUND_VALUE=9,
415
416    /**
417     * The constant used to select the maximum safe rounding value
418     * for a time scale.
419     * 
420     * NOTE: This is an internal value. DO NOT USE IT.
421     * 
422     * @see utmscale_getTimeScaleValue
423     *
424     * @internal ICU 3.2
425     */
426    UTSV_MAX_ROUND_VALUE=10,
427
428#endif /* U_HIDE_INTERNAL_API */
429
430#ifndef U_HIDE_DEPRECATED_API
431    /**
432     * The number of time scale values, in other words limit of this enum.
433     * 
434     * @see utmscale_getTimeScaleValue
435     * @deprecated ICU 59 The numeric value may change over time, see ICU ticket #12420.
436     */
437    UTSV_MAX_SCALE_VALUE=11
438#endif  /* U_HIDE_DEPRECATED_API */
439
440} UTimeScaleValue;
441
442/**
443 * Get a value associated with a particular time scale.
444 * 
445 * @param timeScale The time scale
446 * @param value A constant representing the value to get
447 * @param status The status code. Set to <code>U_ILLEGAL_ARGUMENT_ERROR</code> if arguments are invalid.
448 * @return - the value.
449 * 
450 * @stable ICU 3.2
451 */
452U_STABLE int64_t U_EXPORT2
453    utmscale_getTimeScaleValue(UDateTimeScale timeScale, UTimeScaleValue value, UErrorCode *status);
454
455/* Conversion to 'universal time scale' */
456
457/**
458 * Convert a <code>int64_t</code> datetime from the given time scale to the universal time scale.
459 *
460 * @param otherTime The <code>int64_t</code> datetime
461 * @param timeScale The time scale to convert from
462 * @param status The status code. Set to <code>U_ILLEGAL_ARGUMENT_ERROR</code> if the conversion is out of range.
463 * 
464 * @return The datetime converted to the universal time scale
465 *
466 * @stable ICU 3.2
467 */
468U_STABLE int64_t U_EXPORT2
469    utmscale_fromInt64(int64_t otherTime, UDateTimeScale timeScale, UErrorCode *status);
470
471/* Conversion from 'universal time scale' */
472
473/**
474 * Convert a datetime from the universal time scale to a <code>int64_t</code> in the given time scale.
475 *
476 * @param universalTime The datetime in the universal time scale
477 * @param timeScale The time scale to convert to
478 * @param status The status code. Set to <code>U_ILLEGAL_ARGUMENT_ERROR</code> if the conversion is out of range.
479 * 
480 * @return The datetime converted to the given time scale
481 *
482 * @stable ICU 3.2
483 */
484U_STABLE int64_t U_EXPORT2
485    utmscale_toInt64(int64_t universalTime, UDateTimeScale timeScale, UErrorCode *status);
486
487#endif /* #if !UCONFIG_NO_FORMATTING */
488
489#endif
490
491 
codekingpro/portable-devtools · Team Ai