Bojan Nikolic: Numerical and Quantitative Methods in C++

[website home] | [BN Algorithms]

Separating input, output and computation

In the previous article, we had a simple but functional program to compute the arithmetic mean of five numbers. The program design is not ideal however: it mixes input, output, and computation making it difficult to re-run the program an even a slightly different set of data. In this article we separate the computational part, so that changing inputs does not come close to affecting the part of the program which does the important work.

Improved program: mean_v3

Here is the improved version:

// mean_v3.cpp
// Bojan Nikolic <bojan@bnikolic.co.uk>
// Do not mix input, computation, and output

#include <iostream>

double cmean( const double * data,
          size_t n)
{
  double sum =0;
  for (size_t i =0 ; i < n ; ++i )
  {
    sum += data[i];
  }
  return (sum/n);
}

int main(void)
{
  const double data[] = { 1,2,3,4,5};
  const size_t n = 5;

  std::cout<<"The mean is: "<< cmean(data, n) <<std::endl;
}

The change is that I have separated the computation of the mean to a separate function called cmean, while the input and output code remains in the function main.

The declaration of the function starts with the following lines:

double cmean( const double * data,
              size_t n)

The elements of this declaration have the following meaning:

  • The first double tells the compiler that the function returns a double-precision floating point number.
  • Next token is cmean which the name of the function.
  • The elements inside the parenthesis declare the parameters that the function takes.
  • The parameter const double * data is a pointer to an array of un-changeable double precision floating point numbers. The concept of pointers is key to C and C++ and we begin its discussion below.
  • size_t n is, as before, a parameter which is suitable for sizing or indexing arrays.

The rest of the function is the same as what was in the previous article in the function main.

Discussion

This version improves the readability since it shows exactly where and how the mean is computed. It also allows computation of the mean of more then one set of data, or of several means. For example:

int main(void)
{
  const double data[] = { 1,2,3,4,5};
  const size_t n = 5;

  std::cout<<"The mean is: "<< cmean(data, n) <<std::endl;
  std::cout<<"The mean of all but last number is: "<< cmean(data, n-1) <<std::endl;
}

Computes both the mean and the mean with the last element of the data array excluded.

Relationship between pointers and arrays

This version of the mean program introduces the key concept of pointers. A pointer to a type T is declared as T *. In the above example, the declaration in the function parameter list is:

const double * data

and so this is a pointer to a const double value.

Yet, within the function cmean however, we use this pointer value data in exactly the same way as we used the array variable data of the previous versing of this program. This is an important relationship and can cause some confusion. The reason for interchangeable use is that arrays and pointers are very closely related in C++.

The secret is in the operator []. For arrays, if you call it with i as the parameter, it returns the i+1-th element of the array (the +1 due to the zero-based counting of elements). That is, for example:

const double data[] = { 1,2,3,4,5};
std::cout<< data[3];

Prints the fourth element, which is 4.

For pointers, the same call with i as the parameter returns the value of the variable that is sequentially the i+1-th variable away in the memory. But elements of arrays are stored sequentially in memory, so this also returns the i+1-th element of the array. In an example:

const double data[] = { 1,2,3,4,5};
const double * pdata = data;
std::cout<< pdata[3];

Also returns the number 4.

Summary

This version of the mean program simplifies it by separating computation from input and output. It also introduces the concept pointers, which will come up a number of times in this series of articles. The next article makes a further improvement to readability and maintainability of this program.