views:

371

answers:

5

Hi,

I want to test the speed of an algorithm, what DateTime overload will give me the most precise time? (I still need day/month/year/seconds but then I want milliseconds also).

+11  A: 

Try using System.Diagnostics.Stopwatch to do this:

http://msdn.microsoft.com/en-us/library/system.diagnostics.stopwatch.aspx

lexx
that's probably more in the spirit of what the OP is asking actually - @OP use ElapsedTicks on the stopwatch for fine grain
annakata
Yes, the OP would probably be better off with a Stopwatch.
Samuel
+4  A: 

Others have mentioned Stopwatch, which is indeed a good idea. However, I have a different approach: I try to measure the algorithm for long enough that the normal system timer resolution would be adequate. (I generally still use Stopwatch, as it's the right type for the job, but it wouldn't matter.) For example, in my recent IO testing I only bother to report seconds, because my tests take minutes (sometimes half an hour) to run. At that point, milliseconds are inappropriate, because they'd be lost in the noise of other processes interrupting etc.

It's not always possible to run tests for that long of course, but it's a nice thing to do where you can. For shorter tests, I'd be wary of benchmarks which take less than about 5 seconds... a brief bit of activity from another process can have a disproportionate effect.

Another thing to consider - measure CPU time instead of wall time:

   [DllImport("kernel32.dll")]
   [return: MarshalAs(UnmanagedType.Bool)]
   static extern bool GetProcessTimes(IntPtr hProcess, 
      out FILETIME lpCreationTime, 
      out FILETIME lpExitTime,
      out ulong lpKernelTime,
      out ulong lpUserTime);

   static ulong GetTime(Process process)
   {
       FILETIME lpCreationTime, lpExitTime;
       ulong lpKernelTime, lpUserTime;

       GetProcessTimes(process.Handle, out lpCreationTime,
                       out lpExitTime, out lpKernelTime, out lpUserTime);

       return lpKernelTime + lpUserTime;
   }
Jon Skeet
+1  A: 

What about using DateTime.Now.Ticks?

Store the value, run the algorithm, compare the stored value to the current value and there's the number of ticks it took to run the algorithm.

kiswa
+1  A: 

When you subtract two DateTime structures, you get a TimeSpan structure. Using TimeSpan you can get the interval between the two times.

var before = DateTime.Now;
System.Threading.Thread.Sleep(6500);
var after = DateTime.Now;

var timeTaken = after - before;
var secondsTaken = timeTaken.TotalSeconds;
var milisecondsTaken = timeTaken.TotalMiliseconds;

Note you have to use TotalXXXX to get all of the XXXX otherwise it will be more like what a human would want. In this case timeTaken.Seconds = 5 but timeTaken.TotalSeconds = 65.

Samuel
Why use DateTime when Stopwatch gives a more accurate timer and you don't need to worry about things like Seconds vs TotalSeconds?
Jon Skeet
He did ask for a DateTime solution, so here it is. But I would recommend using a Stopwatch.
Samuel
A: 

Here is a code example for using the System.Diagnostics.Stopwatch class:

Stopwatch sw = Stopwatch.StartNew();
// Put the code here that you want to time
sw.Stop();
long elapsedTime = sw.ElapsedMilliseconds;

DateTime.Ticks is only accurate to within about 15 ms, so is not ideal for timing short algorithms.

Patrick McDonald