Measuring Execution Time in C# by ger


Motivation

Sometimes, while writing programs, we can get into situations when we need to measure execution times of various tasks.

Each programming language provides some mechanism to retrieve the current time from the system. If we read and store the system time at various moments, we can compute time intervals by substracting the values of system time taken at diffent moments.

We will see how to read the system time and how to measure time intervals in C#.

Reading the system time in C#

In C#, the DateTime class is used for storing the value of the system time at a specified moment. A DateTime instance stores both date and time information. The DateTime class can be found in the System namespace.

In order to retrieve the current system time, we can use the static property Now of the DateTime class. For example the following two lines of code

 DateTime currentSystemTime = DateTime.Now; Console.WriteLine(currentSystemTime);

print out something like this:

 4/17/2005 4:05:35 PM

We can print the date and time information stored in a DateTime instance in various formats, but we do not focus on them here, since our purpose is only to see how to measure time intervals.

Measuring time intervals in C#

In C#, there exists a dedicated class that stores information about a time interval. The name of the class is TimeSpan and it can be found in the System namespace.

The TimeSpan class is very easy to use. If we have an instance of TimeSpan class, we can assign to it directly a difference of two DateTime instance. See the code below to see how to do this.

 /* Read the initial time. */ 
 DateTime startTime = DateTime.Now; Console.WriteLine(startTime); 
 /* Do something that takes up some time. For example sleep for 1.7 seconds. */ 
 Thread.Sleep(1700); 
 /* Read the end time. */ 
 DateTime stopTime = DateTime.Now; 
 Console.WriteLine(stopTime); 
 /* Compute the duration between the initial and the end time. */ 
 TimeSpan duration = stopTime - startTime; 
 Console.WriteLine(duration);

The output of this code looks something like this:

 4/17/2005 4:12:30 PM 4/17/2005 4:12:31 PM 00:00:01.7224768

As we see, by default the time interval is printed in the format hh:mm:ss.msec. If we want to retrieve separately the number of hours, minutes, seconds or milliseconds, we can do it through the properties of the TimeSpan class. Look at the code below to see how to do this.

 /* Read the initial time. */ 
 DateTime startTime = DateTime.Now; 
 Console.WriteLine(startTime); 
 /* Do something that takes up some time. For example sleep for 1.7 seconds. */ 
 Thread.Sleep(1700); 
 /* Read the end time. */ 
 DateTime stopTime = DateTime.Now; 
 Console.WriteLine(stopTime); 
 /* Compute the duration between the initial and the end time. * Print out the number of elapsed hours, minutes, seconds and milliseconds. */ 
 TimeSpan duration = stopTime - startTime; 
 Console.WriteLine("hours:" + duration.Hours); 
 Console.WriteLine("minutes:" + duration.Minutes); 
 Console.WriteLine("seconds:" + duration.Seconds); 
 Console.WriteLine("milliseconds:" + duration.Milliseconds);

The result of running this code is something like this:

 4/17/2005 4:17:28 PM 4/17/2005 4:17:30 PM hours:0 minutes:0 seconds:1 milliseconds:712

If we look more attentively, we will realize that this mode of retrieving the hours, minutes, seconds and milliseconds is not very useful. Because each field is returned separately and if we want to find out the total number of hours, minutes or seconds or milliseconds we have to manually sum up the individual fields.

Luckily, the TimeSpan class also provides some properties for directly retrieving the total elapsed hours, minutes, seconds and milliseconds. Look at the following code to see how these properties can be read.

 /* Read the initial time. */ 
 DateTime startTime = DateTime.Now; 
 Console.WriteLine(startTime); 
 /* Do something that takes up some time. For example sleep for 1.7 seconds. */ 
 Thread.Sleep(1700); 
 /* Read the end time. */ 
 DateTime stopTime = DateTime.Now; 
 Console.WriteLine(stopTime); 
 /* Compute the duration between the initial and the end time. * Print out the number of elapsed hours, minutes, seconds and milliseconds. */ 
 TimeSpan duration = stopTime - startTime; 
 Console.WriteLine("hours:" + duration.TotalHours); 
 Console.WriteLine("minutes:" + duration.TotalMinutes); 
 Console.WriteLine("seconds:" + duration.TotalSeconds); 
 Console.WriteLine("milliseconds:" + duration.TotalMilliseconds);

The result of this code is something like:

 4/17/2005 4:23:27 PM 4/17/2005 4:23:29 PM hours:0.000475684 minutes:0.02854104 seconds:1.7124624 milliseconds:1712.4624

Which is indeed much more useful, isn’t it?

More advanced operations on time intervals

C# allows more advanced operations on time intervals. For example we can compute the sum of two TimeSpan instances, and the result is also of TimeSpan type.

Look at the following code to see how we can measure two separate time intervals and then easily compute the total execution time.

 /* Read the initial time. */ 
 DateTime startTime1 = DateTime.Now; 
 /* Do something that takes up some time. For example sleep for 1.7 seconds. */ 
 Thread.Sleep(1700); 
 /* Read the end time. */ 
 DateTime stopTime1 = DateTime.Now; 
 /* Compute and print the duration of this first task. */ 
 TimeSpan duration1 = stopTime1 - startTime1; 
 Console.WriteLine("First task duration: {0} milliseconds.", duration1.TotalMilliseconds); 
 /* Do something that does not have to be measured. * For example sleep for a while. */ 
 Thread.Sleep(900); 
 /* Now we want to measure another task. We store the start time. */ 
 DateTime startTime2 = DateTime.Now; 
 /* We perform the second task which again takes up some time. * For example we can sleep for 2.1 seconds. */ 
 Thread.Sleep(2100); 
 /* We store the end time of the second task. */ 
 DateTime stopTime2 = DateTime.Now; 
 /* Compute and print the duration of this second task. */ 
 TimeSpan duration2 = stopTime2 - startTime2; 
 Console.WriteLine("Second task duration: {0} milliseconds.", duration2.TotalMilliseconds); 
 /* Compute the total execution time. */ 
 TimeSpan totalDuration = duration1 + duration2; 
 Console.WriteLine("Total duration: {0} milliseconds.", totalDuration.TotalMilliseconds);

The ouput obtained by running this code is:

First task duration: 1702.448 milliseconds. Second task duration: 2103.024 milliseconds. Total duration: 3805.472 milliseconds.

In the same manner we can compute the difference between two TimeSpan instances. Again the result will be of TimeSpan type.

Conclusions

As we could see, the combination of DateTime and TimeSpan classes is very powerfull. It allows us to very easily record the system time and then measure execution times. These two classes can save us a lot of headaches if we know about their existence.