# 2.11 Add and Subtract Dates and Times

## 2.11 Add and Subtract Dates and Times

### Problem

You need to perform calculations with dates and times.

### Solution

Use the TimeSpan and DateTime structures, both of which provide Add and Subtract methods .

### Discussion

The .NET Framework provides two structures for manipulating date and time information. The DateTime structure stores a reference to a single date and time (such as January 20, 2004 at 12:00 AM). The TimeSpan structure stores an interval of time (such as three hours). TimeSpan is ultimately measured in ticks (a unit of time equal to 100 nanoseconds), and DateTime is stored as the number of ticks since 12:00:00 midnight, January 1, 0001 C.E. The greater a DateTime is, the later the date. The greater a TimeSpan is, the larger the interval of time.

There are several ways to use DateTime and TimeSpan to perform calculations. All of the following are valid options:

• Use the DateTime.Add or DateTime.Subtract method with a TimeSpan value (which returns a new DateTime ).

• Use DateTime.Subtract with a DateTime value (which returns a TimeSpan representing the difference).

• Combine two TimeSpan values using the TimeSpan.Add or TimeSpan.Subtract method (both of which return a new TimeSpan ).

• Use a higher-level DateTime method such as AddDays , AddHours , AddMinutes , and so on. These methods return a new DateTime and can accept negative numbers .

For example, here is how you might check the current time against a fixed expiration date:

```If DateTime.Now > (ExpirationDate.AddDays(30)) ' More than thirty days have elapsed since expiration date. End If
```

Here's how you can benchmark code:

```Dim InitialTime As Date = DateTime.Now ' (Insert the code to benchmark here, or make the appropriate function calls.) Dim ElapsedTime As TimeSpan = DateTime.Now.Subtract(InitialTime) Console.WriteLine("Total time: " & ElapsedTime.TotalSeconds.ToString())
```

Here's one way you could delay code in a loop for a specified interval of time (although using Thread.Sleep is a more efficient approach).

```Dim InitialTime As DateTime = DateTime.Now Dim WaitSpan As TimeSpan = TimeSpan.FromSeconds(10) Dim LoopTime As TimeSpan ' Wait for 10 seconds. Do LoopTime = DateTime.Now.Subtract(InitialTime) Loop Until TimeSpan.Compare(LoopTime, WaitSpan) = 1
```

Note that you can't use the comparison operators (< and >) with dates. However, you can retrieve a number that represents the TimeSpan interval, using properties such as TotalHours , TotalMinutes , TotalMilliseconds , or Ticks . The code below rewrites the time delay loop with a more readable equivalent using the TimeSpan.Ticks property.

```' Wait for 10 seconds. Do LoopTime = DateTime.Now.Subtract(InitialTime) Loop Until LoopTime.Ticks > WaitSpan.Ticks
```

## 2.12 Determine Days of the Week, Leap Years, and More

### Problem

You want to determine date information, such as what day of the week a given date falls on, whether a year is a leap year, and how many days are in a month.

### Solution

Use a Calendar -derived class from the System.Globalization namespace, such as GregorianCalendar , or use the properties of a DateTime object.

### Discussion

The System.Globalization namespace includes classes that contain culture- related calendar information. These classes derive from the base class Calendar and include GregorianCalendar (the Western standard), HebrewCalendar , JulianCalendar , JapaneseCalendar , and so on.

The Calendar classes define a number of basic methods , including:

• GetDaysInMonth returns the number of days in a given month.

• GetDaysInYear returns the number of days in a given year.

• IsLeapYear returns True if the specified year is a leap year.

• Methods that require you to supply a DateTime instance, such as GetDayOfWeek , GetDayOfYear , and so on. This functionality is also available through DateTime properties.

```Dim Calendar As New System.Globalization.GregorianCalendar() Console.WriteLine("Days in December 2000: " & _ Calendar.GetDaysInMonth(2000, 12, _ Calendar.CurrentEra).ToString()) Console.WriteLine("Is 2004 a leap year? " & _ Calendar.IsLeapYear(2004)) Console.WriteLine("Days in 2004: " & _ Calendar.GetDaysInYear(2004)) Console.WriteLine("Today is a " & _ Calendar.GetDayOfWeek(DateTime.Now).ToString())
```

The output is as follows :

```Days in December 2000: 31 Is 2004 a leap year? True Days in 2004: 366 Today is a Friday
```