Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Newer
Older
100644 127 lines (107 sloc) 4.272 kb
f4b065b Nick Berardi moved around some code from issues #28 and #30 and used DateTimePrecise ...
nberardi authored
1 using System;
2 using System.Diagnostics;
3
4 namespace System
5 {
6 /// DateTimePrecise class in C# -- an improvement to DateTime.Now
7 /// By jamesdbrock
8 /// http://www.codeproject.com/KB/cs/DateTimePrecise.aspx
9 /// Licensed via The Code Project Open License (CPOL) 1.02
10 /// http://www.codeproject.com/info/cpol10.aspx
11 ///
12 /// DateTimePrecise provides a way to get a DateTime that exhibits the
13 /// relative precision of
14 /// System.Diagnostics.Stopwatch, and the absolute accuracy of DateTime.Now.
15 public class DateTimePrecise
16 {
17 private static readonly DateTimePrecise PrivateHelperInstance = new DateTimePrecise(10);
18
19 /// <summary>Returns the current date and time, just like DateTime.Now.</summary>
20 public static DateTime Now
21 {
22 get { return PrivateHelperInstance.GetNow(); }
23 }
24
25 /// <summary>Returns the current date and time, just like DateTime.UtcNow.</summary>
26 public static DateTime UtcNow
27 {
28 get { return PrivateHelperInstance.GetUtcNow(); }
29 }
30
31 /// <summary>Returns the current date and time, just like DateTimeOffset.Now.</summary>
32 public static DateTimeOffset NowOffset
33 {
34 get { return PrivateHelperInstance.GetNowOffset(); }
35 }
36
37 /// <summary>Returns the current date and time, just like DateTimeOffset.UtcNow.</summary>
38 public static DateTimeOffset UtcNowOffset
39 {
40 get { return PrivateHelperInstance.GetUtcNowOffset(); }
41 }
42
43 private const long ClockTickFrequency = 10000000;
44
45 private readonly Stopwatch _stopwatch;
46 private readonly long _synchronizePeriodStopwatchTicks;
47 private DateTimePreciseSafeImmutable _immutable;
48
49 /// <summary>Creates a new instance of DateTimePrecise.
50 /// A large value of synchronizePeriodSeconds may cause arithmetic overthrow
51 /// exceptions to be thrown. A small value may cause the time to be unstable.
52 /// A good value is 10.
53 /// synchronizePeriodSeconds = The number of seconds after which the
54 /// DateTimePrecise will synchronize itself with the system clock.</summary>
55 public DateTimePrecise(long synchronizePeriodSeconds)
56 {
57 _stopwatch = Stopwatch.StartNew();
58 _stopwatch.Start();
59
60 var utc = DateTime.UtcNow;
61 _immutable = new DateTimePreciseSafeImmutable(utc, utc, _stopwatch.ElapsedTicks, Stopwatch.Frequency);
62
63 _synchronizePeriodStopwatchTicks = synchronizePeriodSeconds * Stopwatch.Frequency;
64 }
65
66 /// <summary>Returns the current date and time, just like DateTime.UtcNow.</summary>
67 public DateTime GetUtcNow()
68 {
69 var stopWatchTicks = _stopwatch.ElapsedTicks;
70 var immutable = _immutable;
71
72 if (stopWatchTicks < immutable.ObservedTicks + _synchronizePeriodStopwatchTicks)
73 {
74 return immutable.BaseTime.AddTicks(((
efd5d8c Nick Berardi added Math.Max(1, *) to preven the devide by zero exception in issue #48
nberardi authored
75 stopWatchTicks - immutable.ObservedTicks) * ClockTickFrequency) / (immutable.StopWatchFrequency));
f4b065b Nick Berardi moved around some code from issues #28 and #30 and used DateTimePrecise ...
nberardi authored
76 }
77 else
78 {
79 var utc = DateTime.UtcNow;
80
efd5d8c Nick Berardi added Math.Max(1, *) to preven the devide by zero exception in issue #48
nberardi authored
81 DateTime tBaseNew = immutable.BaseTime.AddTicks(((stopWatchTicks - immutable.ObservedTicks) * ClockTickFrequency) / (immutable.StopWatchFrequency));
f4b065b Nick Berardi moved around some code from issues #28 and #30 and used DateTimePrecise ...
nberardi authored
82
83 _immutable = new DateTimePreciseSafeImmutable(
84 utc,
85 tBaseNew,
86 stopWatchTicks,
efd5d8c Nick Berardi added Math.Max(1, *) to preven the devide by zero exception in issue #48
nberardi authored
87 ((stopWatchTicks - immutable.ObservedTicks) * ClockTickFrequency * 2) / (3 * utc.Ticks - 2 * immutable.ObservedTime.Ticks - tBaseNew.Ticks));
f4b065b Nick Berardi moved around some code from issues #28 and #30 and used DateTimePrecise ...
nberardi authored
88
89 return tBaseNew;
90 }
91 }
92
93 /// <summary>Returns the current date and time, just like DateTime.Now.</summary>
94 public DateTime GetNow()
95 {
96 return GetUtcNow().ToLocalTime();
97 }
98
99 /// <summary>Returns the current date and time, just like DateTimeOffset.UtcNow.</summary>
100 public DateTimeOffset GetUtcNowOffset()
101 {
102 return new DateTimeOffset(GetUtcNow());
103 }
104
105 /// <summary>Returns the current date and time, just like DateTimeOffset.Now.</summary>
106 public DateTimeOffset GetNowOffset()
107 {
108 return new DateTimeOffset(GetNow());
109 }
110
2c77dfc Nick Berardi refactored mutation handling to better handle super columns which fixed ...
nberardi authored
111 private struct DateTimePreciseSafeImmutable
f4b065b Nick Berardi moved around some code from issues #28 and #30 and used DateTimePrecise ...
nberardi authored
112 {
113 public DateTimePreciseSafeImmutable(DateTime observedTime, DateTime baseTime, long observedTicks, long stopWatchFrequency)
114 {
115 ObservedTime = observedTime;
116 BaseTime = baseTime;
117 ObservedTicks = observedTicks;
efd5d8c Nick Berardi added Math.Max(1, *) to preven the devide by zero exception in issue #48
nberardi authored
118 StopWatchFrequency = Math.Max(1, stopWatchFrequency);
f4b065b Nick Berardi moved around some code from issues #28 and #30 and used DateTimePrecise ...
nberardi authored
119 }
120
121 public readonly DateTime ObservedTime;
122 public readonly DateTime BaseTime;
123 public readonly long ObservedTicks;
124 public readonly long StopWatchFrequency;
125 }
126 }
127 }
Something went wrong with that request. Please try again.