Multidimensional Arrays

I l @ ve RuBoard

Multidimensional Arrays

Tempest Cloud, a weather person who takes her subject cirrusly, wants to analyze 5 years of monthly rainfall data. One of her first decisions is how to represent the data. One choice is to use 60 variables , one for each data item. (We mentioned this choice once before, and it is as senseless now as it was then.) Using an array with 60 elements would be an improvement, but it would be nicer still if she could keep each year's data separate. She could use five arrays, each with 12 elements, but that is clumsy and could get really awkward if Tempest decides to study 50 years' worth of rainfall instead of 5. She needs something better.

The better approach is to use an array of arrays. The master array would have five elements, one for each year. Each of those elements, in turn , would be a 12-element array, one for each month. This is how to declare such an array:

 float rain[5][12];  /* array of 5 arrays of 12 floats */ 

You can also visualize this rain array as a two-dimensional array consisting of five rows, each of 12 columns , as shown in Figure 10.3. By changing the second subscript, you move along a row, month by month. By changing the first subscript, you move vertically along a column, year by year.

Figure 10.3. Two-dimensional array.
graphics/10fig03.jpg

The two-dimensional view is merely a convenient way of visualizing an array with two indices. Internally, such an array is stored sequentially, beginning with the first 12-element array, followed by the second 12-element array, and so on.8

Let's use this two-dimensional array in a weather program. The program goal is to find the total rainfall for each year, the average yearly rainfall, and the average rainfall for each month. To find the total rainfall for a year, you have to add all the data in a given row. To find the average rainfall for a given month, you have to add all the data in a given column. The two-dimensional array makes it easy to visualize and execute these activities. Listing 10.12 shows the program.

Listing 10.12 The rain.c program.
 /* rain.c  -- finds yearly totals, yearly average, and monthly                  average for several years of rainfall data */ #include <stdio.h> #define MONTHS 12    /* number of months in a year */ #define YRS   5      /* number of years of data    */ int main(void) {  /* initializing rainfall data for 1990 - 1994 */  const float rain[YRS][MONTHS] = {  {10.2, 8.1, 6.8, 4.2, 2.1, 1.8, 0.2, 0.3, 1.1, 2.3, 6.1, 7.4},  {9.2, 9.8, 4.4, 3.3, 2.2, 0.8, 0.4, 0.0, 0.6, 1.7, 4.3, 5.2},  {6.6, 5.5, 3.8, 2.8, 1.6, 0.2, 0.0, 0.0, 0.0, 1.3, 2.6, 4.2},  {4.3, 4.3, 4.3, 3.0, 2.0, 1.0, 0.2, 0.2, 0.4, 2.4, 3.5, 6.6},  {8.5, 8.2, 1.2, 1.6, 2.4, 0.0, 5.2, 0.9, 0.3, 0.9, 1.4, 7.2}  };  int year, month;  float subtot, total;  printf(" YEAR    RAINFALL  (inches)\n");  for (year = 0, total = 0; year < YRS; year++)  {             /* for each year, sum rainfall for each month */     for (month = 0, subtot = 0; month < MONTHS; month++)        subtot += rain[year][month];     printf("%5d %15.1f\n", 1990 + year, subtot);     total += subtot;                  /* total for all years */  }  printf("\nThe yearly average is %.1f inches.\n\n", total/YRS);  printf("MONTHLY AVERAGES:\n\n");  printf(" Jan  Feb  Mar  Apr  May  Jun  Jul  Aug  Sep  Oct ");  printf(" Nov  Dec\n");  for (month = 0; month < MONTHS; month++)  {               /* for each month, sum rainfall over years */     for (year = 0, subtot =0; year < YRS; year++)        subtot += rain[year][month];     printf("%4.1f ", subtot/YRS);  }  printf("\n");  return 0; } 

Here is the output:

 YEAR    RAINFALL  (inches)  1990            50.6  1991            41.9  1992            28.6  1993            32.2  1994            37.8   The yearly average is 38.2 inches. MONTHLY AVERAGES:  Jan  Feb  Mar  Apr  May  Jun  Jul  Aug  Sep  Oct  Nov  Dec  7.8  7.2  4.1  3.0  2.1  0.8  1.2  0.3  0.5  1.7  3.6  6.1 

As you study this program, concentrate on the initialization and on the computation scheme. The initialization is the more involved of the two, so let's look at the computation first.

To find the total for a given year, keep year constant and let month go over its full range. This is the inner for loop of the first part of the program. Then repeat the process for the next value of year . This is the outer loop of the first part of the program. A nested loop structure like this one is natural for handling a two-dimensional array. One loop handles the first subscript, and the other loop handles the second subscript.

The second part of the program has the same structure, but now it changes year with the inner loop and month with the outer. Remember, each time the outer loop cycles once, the inner loop cycles its full allotment. Therefore, this arrangement cycles through all the years before changing months. You get a 5-year average for the first month, and so on.

Initializing a Two-Dimensional Array

For the initialization, we included five embraced lists of numbers, all enclosed by one outer set of braces. The data in the first interior set of braces is assigned to the first row of the array, the data in the second interior set goes to the second row, and so on. The rules we discussed about mismatches between data and array sizes apply to each row. That is, if the first inner set of braces encloses 10 numbers, only the first 10 elements of the first row are affected. The last two elements in that row are then initialized by default to zero. If there are too many numbers, it is an error; the numbers do not get shoved into the next row.

We could have left out the interior braces and just retained the two outermost braces. As long as you have the right number of entries, the effect is the same. If you are short of entries, however, the array is filled sequentially row by row until the data runs out. Then the remaining elements are initialized to . Figure 10.4 shows both ways of initializing an array.

Figure 10.4. Two methods of initializing an array.
graphics/10fig04.jpg

Because the rain array holds data that should not be modified, the program uses the const modifier when declaring the array.

More Dimensions

Everything we have said about two-dimensional arrays can be generalized to three-dimensional arrays and further. You can declare a three-dimensional array this way:

 int box[10][20][30]; 

You can visualize this array as 10 two-dimensional arrays (each 20 — 30) stacked atop each other, or you can think of it as an array of arrays of arrays. That is, it is a 10-element array, each element of which is a 20-element array. Each 20-element array then has elements that are 30-element arrays. Or you can simply think of arrays in terms of the number of indices needed. We'll stick to two dimensions in our examples.

I l @ ve RuBoard


C++ Primer Plus
C Primer Plus (5th Edition)
ISBN: 0672326965
EAN: 2147483647
Year: 2000
Pages: 314
Authors: Stephen Prata

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net