Working with Structures in C: A Structure for Storing the Date

You can define a structure called date in the C language that consists of three compo- nents that represent the month, day, and year. The syntax for such a definition is rather straightforward,  as follows:

struct date

{

int month;

int day;

int year;

};

The date structure just defined contains three integer members called month, day, and year. The definition of date in a sense defines a new type in the language in that vari- ables can subsequently be declared to be of type struct date, as in the declaration

struct date today;

You can also declare a variable purchaseDate to be of the same type by a separate decla- ration, such as

struct date purchaseDate;

Or, you can simply include the two declarations on the same line, as in

struct date today, purchaseDate;

Unlike variables of type int, float, or char,a special syntax is needed when dealing with structure variables. A member of a structure is accessed by specifying the variable name, followed by a period, and then the member name. For example, to set the value of the day in the variable today to 25, you write

today.day = 25;

Note that there are no spaces permitted between the variable name, the period, and the member name. To set the year in today to 2004, the expression

today.year = 2004;

can be used. Finally, to test the value of month to see if it is equal to 12,a statement such as

if ( today.month == 12 )

nextMonth = 1;

does the trick.

Try to determine the effect of the following statement.

if ( today.month == 1 && today.day == 1 )

printf (“Happy New Year!!!\n”);

Program 9.1 incorporates the preceding discussions into an actual C program.

Program 9.1   Illustrating a Structure

// Program to illustrate a structure

#include <stdio.h>

int main (void)

{

struct date

{

int month;

int day;

int year;

};

struct date today;

today.month = 9;

today.day = 25;

today.year = 2004;

printf (“Today’s date is %i/%i/%.2i.\n”, today.month, today.day, today.year % 100);

return 0;

}

Program 9.1   Output

Today’s date is 9/25/04.

The first statement inside main defines the structure called date to consist of three inte-ger members called month, day, and year. In the second statement, the variable today is declared to be of type struct date. The first statement simply defines what a date structure looks like to the C compiler and causes no storage to be reserved inside the computer. The second statement declares a variable to be of type struct date and, therefore, does cause memory to be reserved for storing the three integer values of the variable today.  Be certain you understand the difference between defining a structure and declaring variables of the particular structure type.

After today has been declared, the program then proceeds to assign values to each of the three members of today, as depicted in Figure 9.1.

After the assignments have been made, the values contained inside the structure are dis- played by an appropriate printf call. The remainder of today.year divided by 100 is calculated prior to being passed to the printf function so that just 04 is displayed for the year. Recall that the format characters %.2i are used to specify that two integer dig- its are to be displayed with zero fill. This ensures that you get the proper display for the last two digits of the year.

1. Using Structures in Expressions

When it comes to the evaluation of expressions, structure members follow the same rules as ordinary variables do in the C language. So division of an integer structure member by another integer is performed as an integer division,  as in

century = today.year / 100 + 1;

Suppose you want to write a simple program that accepts today’s date as input and dis- plays tomorrow’s date to the user. Now, at first glance, this seems a perfectly simple task to perform.You can ask the user to enter today’s date and then proceed to calculate tomorrow’s date by a series of statements, such as

tomorrow.month = today.month;

tomorrow.day   = today.day + 1;

tomorrow.year  = today.year;

Of course, the preceding statements work just fine for the majority of dates, but the fol- lowing two cases are not properly handled:

  1. If today’s date falls at the end of a month.
  2. If today’s date falls at the end of a year (that is, if today’s date is December 31).

One way to determine easily if today’s date falls at the end of a month is to set up an array of integers that corresponds to the number of days in each month. A lookup inside the array for a particular month then gives the number of days in that month. So the statement

int daysPerMonth[12] = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 };

defines an array called daysPerMonth containing 12 integer elements. For each month i, the value contained in daysPerMonth[i – 1] corresponds to the number of days in that particular month. Therefore, the number of days in April, which is the fourth month of the year, is given by daysPerMonth[3], which is equal to 30. (You could define the array to contain 13 elements, with daysPerMonth[i] corresponding to the number of days in month i. Access into the array could then be made directly based on the month num- ber, rather than on the month number minus 1. The decision of whether to use 12 or 13 elements in this case is strictly a matter of personal preference.)

If it is determined that today’s date falls at the end of the month, you can calculate tomorrow’s date by simply adding 1 to the month number and setting the value of the day equal to 1.

To solve the second problem mentioned earlier, you must determine if today’s date is at the end of a month and if the month is 12. If this is the case, then tomorrow’s day and month must be set equal to 1 and the year appropriately incremented by 1.

Program 9.2 asks the user to enter today’s date, calculates tomorrow’s date, and dis-plays the results.

Program 9.2   Determining  Tomorrow’s  Date

// Program to determine tomorrow’s date

#include <stdio.h>

int main (void)

{

struct date

{

int month;

int day;

int year;

};

struct date today, tomorrow;

const int daysPerMonth[12] = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 };

printf (“Enter today’s date (mm dd yyyy): “);

scanf (“%i%i%i”, &today.month, &today.day, &today.year);

if ( today.day != daysPerMonth[today.month – 1] ) {

tomorrow.day = today.day + 1;

tomorrow.month = today.month;

tomorrow.year = today.year;

}

else if ( today.month == 12 ) {   // end of year

tomorrow.day = 1;

tomorrow.month = 1;

tomorrow.year = today.year + 1;

}

else {                        // end of month

tomorrow.day = 1;

tomorrow.month = today.month + 1;

tomorrow.year = today.year;

}

printf (“Tomorrow’s date is %i/%i/%.2i.\n”, tomorrow.month,

tomorrow.day, tomorrow.year % 100);

return 0;

}

Program 9.2   Output

Enter today’s date (mm dd yyyy): 12 17 2004

Tomorrow’s date is 12/18/04.

Program 9.2   Output (Rerun)

Enter today’s date (mm dd yyyy): 12 31 2005

Tomorrow’s date is 1/1/06.

Program 9.2   Output (Second  Rerun)

Enter today’s date (mm dd yyyy): 2 28 2004

Tomorrow’s date is 3/1/04.

If you look at the program’s output, you quickly notice that there seems to be a mistake somewhere: The day after February 28, 2004 is listed as March 1, 2004 and not as February 29, 2004. The program forgot about leap years! You fix this problem in the fol- lowing section. First, you need to analyze the program and its logic.

After the date structure is defined, two variables of type struct date, today and tomorrow, are declared. The program then asks the user to enter today’s date. The three integer values that are entered are stored into today.month, today.day, and today.year, respectively. Next, a test is made to determine if the day is at the end of the month, by comparing today.day to daysPerMonth[today.month – 1]. If it is not the end of the month, tomorrow’s date is calculated by simply adding 1 to the day and set- ting tomorrow’s month and year equal to today’s month and year.

If today’s date does fall at the end of the month, another test is made to determine if it is the end of the year. If the month equals 12, meaning that today’s date is December 31, tomorrow’s date is set equal to January 1 of the next year. If the month does not equal 12, tomorrow’s date is set to the first day of the following month (of the same year).

After tomorrow’s date has been calculated, the values are displayed to the user with an appropriate printf statement call, and program execution is complete.

Source: Kochan Stephen G. (2004), Programming in C: A Complete Introduction to the C Programming Language, Sams; Subsequent edition.

Leave a Reply

Your email address will not be published. Required fields are marked *