Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • World
  • Users
  • Groups
Skins
  • Light
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
Code Project
  1. Home
  2. Other Discussions
  3. The Weird and The Wonderful
  4. DateTime.Now vs. GetSystemTime

DateTime.Now vs. GetSystemTime

Scheduled Pinned Locked Moved The Weird and The Wonderful
cssvisual-studioquestionannouncement
10 Posts 6 Posters 0 Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • B Offline
    B Offline
    Bernhard Hiller
    wrote on last edited by
    #1

    Working with date and time is known to be a source of beautiful code... System.DateTime.Now gets the current system time, but you cannot set it. When you want to be able to set the system time, you can try SetSystemTime(ref SYSTEMTIME lpSystemTime) of kernel32.dll; and there is also a GetSystemTime(ref SYSTEMTIME lpSystemTime) function in that dll. When I played with these functions, I wrote some tests to make sure I got the conversion from struct SYSTEMTIME to System.DateTime and vice versa right.

    [Test]
    public void GetSystemTime()
    {
    DateTime expected = System.DateTime.Now;
    DateTime actual = SystemTime.GetSystemTime();
    Assert.AreEqual(expected, actual);
    }

    Well, that always failed: it takes a tick or two to do all the calculations. I had to update it to allow for some delay:

        \[Test\]
        public void GetSystemTime()
        {
            DateTime expected = System.DateTime.Now;
            DateTime actual = SystemTime.GetSystemTime();
            int delta = Math.Abs(Convert.ToInt32((actual - expected).Ticks));
            int maxDuration = Convert.ToInt32(2 \* TimeSpan.TicksPerMillisecond);
            Assert.Less(delta, maxDuration);
        }
    

    That's 2 Milliseconds for that simple code. But still it fails rather often:

    Errors and Failures:

    1. Test Failure : XY.SystemTimeTests.GetSystemTime
      Expected: less than 20000
      But was: 147763

    What does the computer do during those almost 15 ms? Is this a test for catching the computer asleep?

    P B L 3 Replies Last reply
    0
    • B Bernhard Hiller

      Working with date and time is known to be a source of beautiful code... System.DateTime.Now gets the current system time, but you cannot set it. When you want to be able to set the system time, you can try SetSystemTime(ref SYSTEMTIME lpSystemTime) of kernel32.dll; and there is also a GetSystemTime(ref SYSTEMTIME lpSystemTime) function in that dll. When I played with these functions, I wrote some tests to make sure I got the conversion from struct SYSTEMTIME to System.DateTime and vice versa right.

      [Test]
      public void GetSystemTime()
      {
      DateTime expected = System.DateTime.Now;
      DateTime actual = SystemTime.GetSystemTime();
      Assert.AreEqual(expected, actual);
      }

      Well, that always failed: it takes a tick or two to do all the calculations. I had to update it to allow for some delay:

          \[Test\]
          public void GetSystemTime()
          {
              DateTime expected = System.DateTime.Now;
              DateTime actual = SystemTime.GetSystemTime();
              int delta = Math.Abs(Convert.ToInt32((actual - expected).Ticks));
              int maxDuration = Convert.ToInt32(2 \* TimeSpan.TicksPerMillisecond);
              Assert.Less(delta, maxDuration);
          }
      

      That's 2 Milliseconds for that simple code. But still it fails rather often:

      Errors and Failures:

      1. Test Failure : XY.SystemTimeTests.GetSystemTime
        Expected: less than 20000
        But was: 147763

      What does the computer do during those almost 15 ms? Is this a test for catching the computer asleep?

      P Offline
      P Offline
      Pete OHanlon
      wrote on last edited by
      #2

      Well, if yours was absolutely the only thing thing that ran on the computer, you might expect this to work consistently. Sadly, in a multi-tasking environment, you cannot guarantee that it's going to be accurate.

      B 1 Reply Last reply
      0
      • P Pete OHanlon

        Well, if yours was absolutely the only thing thing that ran on the computer, you might expect this to work consistently. Sadly, in a multi-tasking environment, you cannot guarantee that it's going to be accurate.

        B Offline
        B Offline
        Bernhard Hiller
        wrote on last edited by
        #3

        Pete O'Hanlon wrote:

        cannot guarantee that it's going to be accurate

        But 15 milliseconds?!

        P J 2 Replies Last reply
        0
        • B Bernhard Hiller

          Pete O'Hanlon wrote:

          cannot guarantee that it's going to be accurate

          But 15 milliseconds?!

          P Offline
          P Offline
          Pete OHanlon
          wrote on last edited by
          #4

          Yup. You just need a couple of expensive processes running and that would easily be the case.

          1 Reply Last reply
          0
          • B Bernhard Hiller

            Working with date and time is known to be a source of beautiful code... System.DateTime.Now gets the current system time, but you cannot set it. When you want to be able to set the system time, you can try SetSystemTime(ref SYSTEMTIME lpSystemTime) of kernel32.dll; and there is also a GetSystemTime(ref SYSTEMTIME lpSystemTime) function in that dll. When I played with these functions, I wrote some tests to make sure I got the conversion from struct SYSTEMTIME to System.DateTime and vice versa right.

            [Test]
            public void GetSystemTime()
            {
            DateTime expected = System.DateTime.Now;
            DateTime actual = SystemTime.GetSystemTime();
            Assert.AreEqual(expected, actual);
            }

            Well, that always failed: it takes a tick or two to do all the calculations. I had to update it to allow for some delay:

                \[Test\]
                public void GetSystemTime()
                {
                    DateTime expected = System.DateTime.Now;
                    DateTime actual = SystemTime.GetSystemTime();
                    int delta = Math.Abs(Convert.ToInt32((actual - expected).Ticks));
                    int maxDuration = Convert.ToInt32(2 \* TimeSpan.TicksPerMillisecond);
                    Assert.Less(delta, maxDuration);
                }
            

            That's 2 Milliseconds for that simple code. But still it fails rather often:

            Errors and Failures:

            1. Test Failure : XY.SystemTimeTests.GetSystemTime
              Expected: less than 20000
              But was: 147763

            What does the computer do during those almost 15 ms? Is this a test for catching the computer asleep?

            B Offline
            B Offline
            BobJanova
            wrote on last edited by
            #5

            Setting the system time is something you should almost never do. I hope you had a good reason for that. The system clock on a lot of machines only updates every ~15ms, so any time based test that expects a better resolution than that needs to use a dedicated high definition timer, e.g. QueryPerformanceCounter.

            R 1 Reply Last reply
            0
            • B Bernhard Hiller

              Pete O'Hanlon wrote:

              cannot guarantee that it's going to be accurate

              But 15 milliseconds?!

              J Offline
              J Offline
              Jorgen Andersson
              wrote on last edited by
              #6

              There are a few thing you can test, first prevent switching of the CPU core by setting which core to use:

              Process.GetCurrentProcess().ProcessorAffinity = new IntPtr(1);

              Then make sure your process is having more exclusive access to that core:

              Process.GetCurrentProcess().PriorityClass = ProcessPriorityClass.High;
              Thread.CurrentThread.Priority = ThreadPriority.Highest;

              Just don't blame me if you're messing up your system. :)

              Wrong is evil and must be defeated. - Jeff Ello[^]

              B 1 Reply Last reply
              0
              • J Jorgen Andersson

                There are a few thing you can test, first prevent switching of the CPU core by setting which core to use:

                Process.GetCurrentProcess().ProcessorAffinity = new IntPtr(1);

                Then make sure your process is having more exclusive access to that core:

                Process.GetCurrentProcess().PriorityClass = ProcessPriorityClass.High;
                Thread.CurrentThread.Priority = ThreadPriority.Highest;

                Just don't blame me if you're messing up your system. :)

                Wrong is evil and must be defeated. - Jeff Ello[^]

                B Offline
                B Offline
                Bernhard Hiller
                wrote on last edited by
                #7

                Well, thanks for the hints... When I posted it here in the "Weird and Wonderful" - or the "Coding Horror" section as it was called previously - I chose this forum because the outcome of these simple lines of code is so "weird and wonderful". The little hints won't have much effect: the tests are running in Virtual Machines, there are several more VMs on that host, though almost all of them are "idle" - but you what Windows can do while the machine is idle...

                J 1 Reply Last reply
                0
                • B Bernhard Hiller

                  Well, thanks for the hints... When I posted it here in the "Weird and Wonderful" - or the "Coding Horror" section as it was called previously - I chose this forum because the outcome of these simple lines of code is so "weird and wonderful". The little hints won't have much effect: the tests are running in Virtual Machines, there are several more VMs on that host, though almost all of them are "idle" - but you what Windows can do while the machine is idle...

                  J Offline
                  J Offline
                  Jorgen Andersson
                  wrote on last edited by
                  #8

                  A well, I don't have a clue how ProcessorAffinity is handled on a VM, but probably wrong. I just figured that your 15 ms was because of context switching and was simply curious.

                  Wrong is evil and must be defeated. - Jeff Ello[^]

                  1 Reply Last reply
                  0
                  • B Bernhard Hiller

                    Working with date and time is known to be a source of beautiful code... System.DateTime.Now gets the current system time, but you cannot set it. When you want to be able to set the system time, you can try SetSystemTime(ref SYSTEMTIME lpSystemTime) of kernel32.dll; and there is also a GetSystemTime(ref SYSTEMTIME lpSystemTime) function in that dll. When I played with these functions, I wrote some tests to make sure I got the conversion from struct SYSTEMTIME to System.DateTime and vice versa right.

                    [Test]
                    public void GetSystemTime()
                    {
                    DateTime expected = System.DateTime.Now;
                    DateTime actual = SystemTime.GetSystemTime();
                    Assert.AreEqual(expected, actual);
                    }

                    Well, that always failed: it takes a tick or two to do all the calculations. I had to update it to allow for some delay:

                        \[Test\]
                        public void GetSystemTime()
                        {
                            DateTime expected = System.DateTime.Now;
                            DateTime actual = SystemTime.GetSystemTime();
                            int delta = Math.Abs(Convert.ToInt32((actual - expected).Ticks));
                            int maxDuration = Convert.ToInt32(2 \* TimeSpan.TicksPerMillisecond);
                            Assert.Less(delta, maxDuration);
                        }
                    

                    That's 2 Milliseconds for that simple code. But still it fails rather often:

                    Errors and Failures:

                    1. Test Failure : XY.SystemTimeTests.GetSystemTime
                      Expected: less than 20000
                      But was: 147763

                    What does the computer do during those almost 15 ms? Is this a test for catching the computer asleep?

                    L Offline
                    L Offline
                    Lost User
                    wrote on last edited by
                    #9

                    If you need a higher resolution, use timeGetTime. GetTickCount has a resolution of roughly 10ms, where the timeGetTime function is more accurate.

                    Bastard Programmer from Hell :suss: If you can't read my code, try converting it here[^]

                    1 Reply Last reply
                    0
                    • B BobJanova

                      Setting the system time is something you should almost never do. I hope you had a good reason for that. The system clock on a lot of machines only updates every ~15ms, so any time based test that expects a better resolution than that needs to use a dedicated high definition timer, e.g. QueryPerformanceCounter.

                      R Offline
                      R Offline
                      Rob Philpott
                      wrote on last edited by
                      #10

                      Exactly. That was my thinking too, resolution.

                      Regards, Rob Philpott.

                      1 Reply Last reply
                      0
                      Reply
                      • Reply as topic
                      Log in to reply
                      • Oldest to Newest
                      • Newest to Oldest
                      • Most Votes


                      • Login

                      • Don't have an account? Register

                      • Login or register to search.
                      • First post
                        Last post
                      0
                      • Categories
                      • Recent
                      • Tags
                      • Popular
                      • World
                      • Users
                      • Groups