none
TimeSpan instead of INT and LONG for Timeout, Delay, Sleep etc. etc. RRS feed

  • Question

  • .NET has this wonderful type called TimeSpan

    why isn't it used for in every case where a Timeout or Delay is declared ?

    SqlCommand.CommandTimeout = INT Seconds

    Thread.Sleep = INT Milliseconds

    Not only are INT and LONG difficult to read (198938472 msec = ?) , they are ambiguous !!

    .NET of all places should enforce the use of TimeSpan everywhere it makes sense !

    Wednesday, August 7, 2013 1:05 PM

Answers

  • I think it boils down to the fact that that a general purpose TimeSpan type needed to be at a higher precision than the system API calls.  I expect each API is crafted about its own native resolution.

    The internal resolution of a TimeSpan is 100-nanosecond units.  Abstract calculations involving time can be made using this resolution.  Whereas many system APIs work at a different native time resolution.  Most notably, the system clock is only at a resolution of milliseconds.

    So using one in place of the other would require performing the arithmetic of the conversion between 64-bit integer 100-nanosecond units and 32-bit integer millisecond units.  The cost is very cheap, but not free.  It may also give people the false impression that a delay or timeout of a few microseconds would be possible, or even accurate.

    I agree with you that a time type would make some things more clear, and less ambiguous.  It's not too hard to make one that can implicitly convert between integer milliseconds and your struct type.  You could also provide overloads or extension methods or abstractions that take a TimeSpan and do the conversion.  The conversion would be done at runtime though, so it wouldn't be free.

    But many of the APIs already allow the use of a TimeSpan parameter or result [1] [2] [3] [4] [5], so I'm a bit confused as to why you're so concerned about this.  Thread.Sleep in particular accepts a TimeSpan.

    As for SqlCommand.CommandTimeout, here's an example of fixing that particular API manually.

    static class SqlCommandExtensions
    {
        public static void SetTimeoutTimeSpan( this SqlCommand cmd, TimeSpan t )
        {
            cmd.CommandTimeout = (int)t.TotalMilliseconds;
        }
    
        public static TimeSpan GetTimeoutTimeSpan( this SqlCommand cmd )
        {
            return new TimeSpan( 0, 0, 0, 0, cmd.CommandTimeout );
        }
    }
    

    Some things like constants can be converted at compile time, and such programming techniques will be pervasive when dealing with other physical quantities such as distance, mass, temperature, etc.  C++11, for example, calls for user-defined literals to help programmers represent things like that in code.

    * NOTE: This is my own speculation.  As for the actual reasoning behind the actual design decisions, I'll have to defer to the actual designers of the .NET framework.

    Wednesday, August 7, 2013 1:58 PM