Thursday, March 16, 2017

Programming Challenge 9.7 - Case Study Modification #2

/* Case Study Modification #2 - This program shows the donations made
   to the United Cause by the employees of CK Graphics, Inc. It
   displays the donations in order from lowest to highest and in the
   original order they were received.

   This is a modification of Program 9-19, the United Cause case study
   program. It now can be used with any set of donations. The program
   dynamically allocates the donations array and asks the user to input
   its values.
 
   This is a modification of Program 9-19, the United Cause case study
   program. The arrPtr array is sorted in descending order instead of
   ascending order. */

#include "Utility.h"

/* Function prototypes */
void getDonations(double *, const int);
void initPtrArray(double *[], double *, const int);
void arrSelectSort(double *[], const int);
void displayArray(const double *, const int);
void showArrPtr(double *[], const int);

int main()
{
   /* Dynamically allocated arrays */
   double *donations = nullptr;
   double **arrPtr = nullptr;

   int numDonations = 0;

   cout << "\n\t\tCK Graphics United Cause Donations\n\n"
        << "\tEnter the number of donations we collected: ";
   cin >> numDonations;

   /* Dynamically allocated array */
   donations = new double[numDonations];

   /* Array of pointers to double*/
   arrPtr = new double *[numDonations];

   /* Initializes arrPtr */
   initPtrArray(arrPtr, donations, numDonations);

   /* Gets the donations from the user */
   getDonations(donations, numDonations);

   /* Sorts the array with an selection sort algorithm */
   arrSelectSort(arrPtr, numDonations);

   /* Displays the donations using the array of pointers in
      sorted order */
   showArrPtr(arrPtr, numDonations);

   /* Display the donations in sorted order */
   displayArray(donations, numDonations);

   /* Frees the memory */
   delete[] arrPtr;
   delete[] donations;

   donations = nullptr;
   arrPtr = nullptr;

   pauseSystem();
   return 0;
}

/* **********************************************************
   Definition: initPtrArray

   This function accepts arrPtr, donations, and numDonations
   indicating the number of elements in the array of pointers
   and in donations as arguments. It initializes the elements
   in arrPtr, then it makes each element point to an element
   in donations.
   ********************************************************** */

void initPtrArray(double *arrPtr[], double *donations, const int numDonations)
{
   for (int index = 0; index < numDonations; index++)
   {
      *(arrPtr + index) = { nullptr };
   }

   for (int index = 0; index < numDonations; index++)
   {
      *(arrPtr + index) = &donations[index];
   }
}

/* **********************************************************
   Definition: getDonations

   This function accepts donations and numDonations as its
   arguments. It asks the user for the amount of donations
   and stores it in the array.
   ********************************************************** */

void getDonations(double *donations, const int numDonations)
{
   cout << "\n";
   for (int index = 0; index < numDonations; index++)
   {
      cout << "\tDonation #" << setw(3) << right << (index + 1)
         << ": $ ";
      cin >> *(donations + index);
   }
}

/* **********************************************************
   Definition: displayArray

   This function accepts donations and numDonations as its
   arguments. It displays the contents of arrPtr.
   ********************************************************** */

void displayArray(const double *donations, const int numDonations)
{
   int index = 0;

   cout << "\n\tThe donations, in their original order are: \n";
   for (int index = 0; index < numDonations; index++)
   {
      cout << "\n\tDonation #" << setw(3) << right
           << (index + 1) << ": $ ";
      cout << setw(8) << right << *(donations + index) << " ";
   }
}

/* **********************************************************
   Definition: arrSelectSort

   This accepts arrPtr and numDonations as its arguments. It
   performs an descending order selection sort on arrPtr,
   which is an array of pointers. Each element of the array
   points to an element of a second array. After sorting the
   elements, arrPtr will point to the elements of the second
   array in ascending order.
   ********************************************************** */

void arrSelectSort(double *arrPtr[], int numDonations)
{
   int startScan = 0,
       maxIndex = 0;

   double *maxElem;

   for (startScan = 0; startScan < (numDonations - 1); startScan++)
   {
      maxIndex = startScan;
      maxElem = arrPtr[startScan];

      for(int index = startScan + 1; index < numDonations; index++)
      {
         if (*(arrPtr[index]) > *maxElem)
         {
            maxElem = arrPtr[index];
            maxIndex = index;
         }
      }
      arrPtr[maxIndex] = arrPtr[startScan];
      arrPtr[startScan] = maxElem;
   }
}

/* **********************************************************
   Definition: showArrPtr

   This function accepts arrPtr and numDonations as its
   arguments. It displays the contents of the array pointed
   to by arrPtr.
   ********************************************************** */

void showArrPtr(double *arrPtr[], const int numDonations)
{
   cout << fixed << showpoint << setprecision(2);

   cout << "\n\tThe donations, sorted in descending order are: \n";

   for (int index = 0; index < numDonations; index++)
   {
      cout << "\n\tDonation #" << setw(3) << right << (index + 1)
           << ": $ ";
      cout << setw(8) << right << *(arrPtr[index]) << " ";
   }
   cout << "\n";
}

Example Output:




Programming Challenge 9.6 - Case Study Modification #1

/* Case Study Modification #1 - This program shows the donations made
   to the United Cause by the employees of CK Graphics, Inc. It
   displays the donations in order from lowest to highest and in the
   original order they were received.

   This is a modification of Program 9-19, the United Cause case study
   program. It now can be used with any set of donations. The program
   dynamically allocates the donations array and asks the user to input
   its values. */

#include "Utility.h"

/* Function prototypes */
void getDonations(double *, const int);
void initPtrArray(double *[], double *, const int);
void arrSelectSort(double *[], const int);
void displayArray(const double *, const int);
void showArrPtr(double *[], const int);

int main()
{
   /* Dynamically allocated arrays */
   double *donations = nullptr;
   double **arrPtr = nullptr;

   int numDonations = 0;

   cout << "\n\t\tCK Graphics United Cause Donations\n\n"
        << "\tEnter the number of donations we collected: ";
   cin >> numDonations;

   /* Dynamically allocated array */
   donations = new double[numDonations];

   /* Array of pointers to double*/
   arrPtr = new double *[numDonations];

   /* Initializes arrPtr */
   initPtrArray(arrPtr, donations, numDonations);

   /* Gets the donations from the user */
   getDonations(donations, numDonations);

   /* Sorts the array with an selection sort algorithm */
   arrSelectSort(arrPtr, numDonations);

   /* Displays the donations using the array of pointers in
      sorted order */
   showArrPtr(arrPtr, numDonations);

   /* Display the donations in sorted order */
   displayArray(donations, numDonations);

   /* Frees the memory */
   delete[] arrPtr;
   delete[] donations;

   donations = nullptr;
   arrPtr = nullptr;

   pauseSystem();
   return 0;
}

/* **********************************************************
   Definition: initPtrArray

   This function accepts arrPtr, donations, and numDonations
   indicating the number of elements in the array of pointers
   and in donations as arguments. It initializes the elements
   in arrPtr, then it makes each element point to an element
   in donations.
   ********************************************************** */

void initPtrArray(double *arrPtr[], double *donations, const int numDonations)
{
   for (int index = 0; index < numDonations; index++)
   {
      *(arrPtr + index) = { nullptr };
   }

   for (int index = 0; index < numDonations; index++)
   {
      *(arrPtr + index) = &donations[index];
   }
}

/* **********************************************************
   Definition: getDonations

   This function accepts donations and numDonations as its
   arguments. It asks the user for the amount of donations
   and stores it in the array.
   ********************************************************** */

void getDonations(double *donations, const int numDonations)
{
   cout << "\n";
   for (int index = 0; index < numDonations; index++)
   {
      cout << "\tDonation #" << setw(3) << right << (index + 1)
         << ": $ ";
      cin >> *(donations + index);
   }
}

/* **********************************************************
   Definition: displayArray

   This function accepts arrPtr and numDonations as its
   arguments. It displays the contents of arrPtr.
   ********************************************************** */

void displayArray(const double *donations, const int numDonations)
{
   int index = 0;

   cout << "\n\tThe donations, in their original order are: \n";
   for (int index = 0; index < numDonations; index++)
   {
      cout << "\n\tDonation #" << setw(3) << right
           << (index + 1) << ": $ ";
      cout << setw(8) << right << *(donations + index) << " ";
   }
}

/* **********************************************************
   Definition: arrSelectSort

   This accepts arrPtr and numDonations as its arguments. It
   performs an ascending order selection sort on arrPtr,
   which is an array of pointers. Each element of the array
   points to an element of a second array. After sorting the
   elements, arrPtr will point to the elements of the second
   array in ascending order.
   ********************************************************** */

void arrSelectSort(double *arrPtr[], int numDonations)
{
   int startScan = 0,
       minIndex = 0;

   double *minElem;

   for (startScan = 0; startScan < (numDonations - 1); startScan++)
   {
      minIndex = startScan;
      minElem = arrPtr[startScan];

      for(int index = startScan + 1; index < numDonations; index++)
      {
         if (*(arrPtr[index]) < *minElem)
         {
            minElem = arrPtr[index];
            minIndex = index;
         }
      }
      arrPtr[minIndex] = arrPtr[startScan];
      arrPtr[startScan] = minElem;
   }
}

/* **********************************************************
   Definition: showArrPtr

   This function accepts arrPtr and numDonations as its
   arguments. It displays the contents of the array pointed
   to by arrPtr.
   ********************************************************** */

void showArrPtr(double *arrPtr[], const int numDonations)
{
   cout << fixed << showpoint << setprecision(2);

   cout << "\n\tThe donations, sorted in ascending order are: \n";

   for (int index = 0; index < numDonations; index++)
   {
      cout << "\n\tDonation #" << setw(3) << right << (index + 1)
           << ": $ ";
      cout << setw(8) << right << *(arrPtr[index]) << " ";
   }
   cout << "\n";
}

Example Output:





Wednesday, March 15, 2017

Programming Challenge 9.5 - Pointer Rewrite

/* Pointer Rewrite - The following function uses reference variables as
   parameters.
  
      int doSomething(int &x, int &y)
      {
         int temp = x;
         x = y * 10;
         y = temp * 10;
         return x + y;
      }

   This program demonstrates the function using pointers instead of
   reference variables. */

#include "Utility.h"

/* Function prototypes */
void getNumbers(int *, int *);
int doSomething(int *, int *);

int main()
{
   int varX = 0,
       varY = 0,
       result = 0;

   /* Pointer variables pointing to integers */
   int *x = nullptr;
   int *y = nullptr;

   /* Pointers x and y are storing the
      addresses of varX and varY */
    x = &varX;
    y = &varY;

    cout << "\n\t\t\tDo Something - Function Demonstration\n";

    cout << "\n\n\tIn Main Function:\n\n"
         << "\tThe initial value of variable varX is " << *x
         << " and its address in memory is " << x;

    cout << "\n\tThe initial value of variable varY is " << *y
         << " and its address in memory is " << y << "\n\n";

    /* Asks the user for two integer values */
    getNumbers(x, y);

    cout << "\n\n\tBack In Main Function:\n\n"
         << "\tThe new value of variable varX is " << *x
         << " and its address in memory is " << x;

    cout << "\n\tThe new value of variable varY is " << *y
         << " and its address in memory is " << y << "\n\n";   

    cout << "\n\tNow performing some calculations using your "
         << "numbers in doSomething() ...\n\n";

   /* Performs some calculations on the variables pointed to
      by *x and *y */
   result = doSomething(x, y);

   cout << "\n\tBack In Main Function:\n\n";

   cout << "\tThe new value of variable varX is " << *x
        << " and its address in memory is " << x;

   cout << "\n\tThe new value of variable varY is " << *y
        << " and its address in memory is " << y << "\n\n";

   cout << "\tThe result of the calculations performed "
        << "in doSomething() is: "
        << *x << " + " << *y << " = " << result << "\n\n";

   pauseSystem();
   return 0;
}


/* **********************************************************
   Definition: getNumbers

   This function accepts two pointers to integers as its
   arguments. It gets two values for x and y from the user.
   ********************************************************** */

void getNumbers(int *x, int *y)
{
   cout << "\n\tPlease enter two numbers:\n"
           << "\tx: ";
   cin >> *x;

   cout << "\ty: ";
   cin >> *y;
}

/* **********************************************************
   Definition: doSomething

   This function accepts to pointers as its arguments. Three
   calculations are performed:

      * x gets the result of multiplying the value pointed to
            by *y by 10
      * y gets the result of multiplying the value pointed to
            by *x assigned to temp by * 10
      * x pointing to valX and y pointing to valY are added
            and this result is returned.

   This final calculation is performed directly in the return
   statement.
   ********************************************************** */

int doSomething(int *x, int *y)
{
   int temp = *x;

   *x = *y * 10;
   *y = temp * 10;

   return (*x + *y);
}

Example Output:



Tuesday, March 14, 2017

Programming Challenge 9.4 - Test Scores #2

/* Test Scores #2 - This program dynamically allocates an array large
   enough to hold a user-defined number of test scores. Once all scores
   are entered, the array is passed to a function that sorts them in
   ascending order.

   Another function is called that calculates the average score. The
   p rogram displays the sorted list of scores and averages with
   appropriate headings. Pointer notation is used rather than array
   notation whenever possible.

   Input Validation: No negative numbers for test scores is accepted.
  
   This is a modification of Programming Challenge 2. It allows the user
   to enter name-score pairs. For each student taking a test, the user
   types the student's name followed by the student's integer test scores.
  
   The sorting function is modified so it takes an array holding the
   student names and an array holding the student test scores. When the
   sorted list of scores is displayed, each student's name is displayed
   along with his or her score. In stepping through the arrays, pointers
   are used rather than array subscripts. */

#include "Utility.h"

/* Function prototypes */
void mainMenu();
void displayIntro();
void displayMenuItems();
void getTestScores(int *, string *, const int);
void sortScores(int *, string *, const int);
double calcAverage(int *, const int);
void displayResults(const int *, const string *,
                    const double, const int);

int main()
{
   mainMenu();

   pauseSystem();
   return 0;
}

/* **********************************************************
   Definition: mainMenu

   Allows the user to select from the following items:

      * View Introduction
      * Enter Test-Scores
      * View Score-Data
      * Quit

   It takes care of calling the necessary functions, passing
   and receiving results, and freeing up the memory when the
   user decides to quit the program.
   ********************************************************** */

void mainMenu()
{
   /* Dynamically allocated arrays */
   int *testScores = nullptr;
   string *studentNames = nullptr;

   const int DISPLAY_INTRODUCTION = 1,
             GET_TEST_SCORES = 2,
             VIEW_RESULTS = 3,
             QUIT = 4;

   int menuItem = 0,
       numScores = 0;

   double averageScore = 0.0;

   do
   {
      displayMenuItems();
      cin >> menuItem;

      /* Validate input */
      while (menuItem < DISPLAY_INTRODUCTION || menuItem > QUIT)
      {
         cout << "\n\tInvalid menu item selected!\n"
              << "\tYour choice: ";
         cin >> menuItem;
      }

      switch (menuItem)
      {
         case DISPLAY_INTRODUCTION:
         {
            displayIntro();
         }
         break;

         case GET_TEST_SCORES:
         {
            /* Get the number of scores (at least three) */
            cout << "\n\tHow many test-scores do you wish to enter? ";
            cin >> numScores;

            cout << "\n";

            /* Dynamically allocates two arrays to hold the number of
               test scores and the student names */
            testScores = new int[numScores];
            studentNames = new string[numScores];

            /* Gets the number of scores entered by the user */
            getTestScores(testScores, studentNames, numScores);

            /* Sorts the scores and student names with an ascending-order
               selection sort algorithm */
            sortScores(testScores, studentNames, numScores);

            /* Calculates the average score and returns the result */
            averageScore = calcAverage(testScores, numScores);
         }
         break;

         case VIEW_RESULTS:
         {
            /* Displays the data after sorting the scores and
               calculating the average */
            displayResults(testScores, studentNames, averageScore, numScores);
         }
         break;

         case QUIT:
         {
            cout << "\n\tDoing a little housekeeping ... ";

            /* Free up memory */
            delete[] testScores;
            delete[] studentNames;
            testScores = nullptr;
            studentNames = nullptr;

            cout << "\n\ttestScores cleared: " << testScores
                 << "\n\tstudentNames cleared: " << studentNames
                 << "\n\tPress enter to close this window!\n";
         }
         break;
      }
   } while (menuItem != QUIT); 
}

/* **********************************************************
   Definition: displayMenuItems

   This function displays the menu items the user can select
   between.
   ********************************************************** */

void displayMenuItems()
{
   cout << "\n\n\t\tAVERAGE TEST SCORE CALCULATOR\n\n"
        << "\t1. View Introduction\n"
        << "\t2. Enter Test-Scores\n"
        << "\t3. View Score-Data\n"
        << "\t4. Quit\n\n"
        << "\tYour choice: ";
}

/* **********************************************************
   Definition: displayIntroduction

   This function introduces the program and how it works to
   the user.
   ********************************************************** */

void displayIntro()
{
   cout << "\n\n\t\tAVERAGE TEST SCORE CALCULATOR\n\n"
        << "\tThis program allows you to enter a number of scores to\n"
        << "\tbe averaged, along with the student names who have taken\n"
        << "\ta test in your class.\n\n"
        << "\tAfter you have entered all of your student's names and\n"
        << "\tscores, the scores and student names are sorted in ascending\n"
        << "\torder, based on their scores. The class average will then be\n"
        << "\tcalculated.\n\n"
        << "\tOnce finished, you can view the results by choosing item '3'\n"
        << "\tfrom the main menu.\n\n";
}

/* **********************************************************
   Definition: getTestScores

   This function accepts testScores and numScores, containing
   the number of elements to be stored in the array, as its
   arguments. It gets the scores and student names to be
   stored in testScore and studentNames.
   ********************************************************** */

void getTestScores(int *testScores, string *studentNames, const int numScores)
{
      for (int index = 0; index < numScores; index++)
      {
         cout << "\n\tStudent Name: ";
         cin >> *(studentNames + index);

         cout << "\tScore #" << (index + 1) << ": ";
         cin >> *(testScores + index);

         /* Validate Input */
         while ((*(testScores + index) <= 0) ||
                (*(testScores + index) > 100.0))
         {
            cout << "\n\t\tYou entered an invalid score!\n\n";
            cout << "\tScore #" << (index + 1) << ": ";
            cin >> *(testScores + index);
         }
      }
      cout << "\n";
}

/* **********************************************************
   Definition: sortScores

   This function accepts testScores, studentNames, and
   numScores, containing the number of elements stored
   in the array, as arguments. An ascending-order selection
   sort is performed on the elements stored in both arrays.
   ********************************************************** */

void sortScores(int *testScores, string *studentNames, const int numScores)
{
   int startScan = 0,
       minIndex = 0,
       minElem = 0,
       index = 0;

   string tempNames = " ";
 
   for (startScan = 0; startScan < (numScores - 1); startScan++)
   {
      minIndex = startScan;
      minElem = *(testScores + startScan);
      tempNames = *(studentNames + startScan);

      for (index = startScan + 1; index < numScores; index++)
      {
         if (*(testScores + index) < minElem)
         {
            minElem = *(testScores + index);
            tempNames = *(studentNames + index);
            minIndex = index;
         }
      }

      *(testScores + minIndex) = *(testScores + startScan);
      *(studentNames + minIndex) = *(studentNames + startScan);
      *(testScores + startScan) = minElem;
      *(studentNames + startScan) = tempNames;
   }
}

/* **********************************************************
   Definition: calcAverage

   This function accepts testScores and numScores as its
   argument. It steps through the array to total the scores,
   then calculates and returns the average.
   ********************************************************** */

double calcAverage(int *testScores, const int numScores)
{
   double total = 0.0,
          average = 0.0;

   for (int count = 0; count < numScores; count++)
   {
      total += *(testScores + count);
   }

   /* Calculates and returns the average */
   return average = total / numScores;
}

/* **********************************************************
   Definition: displayResults

   This function accepts testScores, studentNames,
   averageScore and numScores as its argument. It displays
   the student name along with his or her score in sorted
   order, and the class average reached on the test.
   ********************************************************** */

void displayResults(const int *testScores, const string *studentNames,
                    const double averageScore, const int numScores)
{
   int index = 0;

   cout << fixed << showpoint << setprecision(2);

   cout << "\n\n\tTHE SCORES IN SORTED ORDER\n";

   cout << "\n\tSTUDENT NAME: " << "\t\t" << "SCORE\n"
        << "\t-------------" << "\t\t" << "-----\n";

   for (index = 0; index < numScores; index++)
   {
      cout << "\t" << setw(9) << left << *(studentNames + index)
         << setw(20) << right << *(testScores + index)
          << " \n" ;
   }
   cout << "\t-------------\n"
        << "\tCLASS AVERAGE:\t" << setw(13) << right
        << averageScore << "\n";
}

Example Output:





Programming Challenge 9.3 - Drop Lowest Score

/* Drop Lowest Score - This program dynamically allocates an array large
   enough to hold a user-defined number of test scores. Once all scores
   are entered, the array is passed to a function that sorts them in
   ascending order.

   Another function is called that calculates the average score. The
   p rogram displays the sorted list of scores and averages with
   appropriate headings. Pointer notation is used rather than array
   notation whenever possible.

   Input Validation: No negative numbers for test scores is accepted.
  
   This is a modification of Programming Challenge 2. The lowest score
   entered by the user is detected and removed, before the scores are
   sorted, and the average is calculated. */

#include "Utility.h"

/* Function prototypes */
void mainMenu();
void displayIntro();
void displayMenuItems();
void getTestScores(double *, const int);
int dropLowestScore(double *, int);
void sortScores(double *, const int);
double calcAverage(double *, const int);
void displayResults(const double *, const double, const int);

int main()
{
   mainMenu();

   pauseSystem();
   return 0;
}

/* **********************************************************
   Definition: mainMenu

   Allows the user to select from the following items:

      * View Introduction
      * Enter Test-Scores
      * View Score-Data
      * Quit

   It takes care of calling the necessary functions, passing
   and receiving results, and freeing up the memory when the
   user decides to quit the program.
   ********************************************************** */

void mainMenu()
{
   /* Dynamically allocated array */
   double *testScores = nullptr;

   const int DISPLAY_INTRODUCTION = 1,
             GET_TEST_SCORES = 2,
             VIEW_RESULTS = 3,
             QUIT = 4;

   int menuItem = 0,
       numScores = 0;

   double averageScore = 0.0;

   do
   {
      displayMenuItems();
      cin >> menuItem;

      /* Validate input */
      while (menuItem < DISPLAY_INTRODUCTION || menuItem > QUIT)
      {
         cout << "\n\tInvalid menu item selected!\n"
              << "\tYour choice: ";
         cin >> menuItem;
      }

      switch (menuItem)
      {
         case DISPLAY_INTRODUCTION:
         {
            displayIntro();
         }
         break;

         case GET_TEST_SCORES:
         {
            /* Get the number of scores (at least three) */
            cout << "\n\tHow many test-scores do you wish to enter?\n"
                 << "\t(3 and above): ";
            cin >> numScores;

            cout << "\n";

            /* Input validation */
            while (numScores < 3)
            {
               cout << "\tInvalid input!\n"
                    << "\tHow many test-scores do you wish to enter? ";
               cin >> numScores;
               cout << "\n";
            }

            /* Dynamically allocates the array to hold the number of
               test scores the user wishes to enter */
            testScores = new double[numScores];

            /* Gets the number of scores entered by the user */
            getTestScores(testScores, numScores);

            /* Sorts the scores with an ascending-order selection sort
               algorithm */
            sortScores(testScores, numScores);

            /* Gets the new number of elements contained in the array,
               finds and drops the lowest score */
            numScores = dropLowestScore(testScores, numScores);

            /* Sorts testScores once more after the lowest score has
               been dropped */
            sortScores(testScores, numScores);

            /* Calculates the average score and returns the result */
            averageScore = calcAverage(testScores, numScores);
         }
         break;

         case VIEW_RESULTS:
         {
            /* Displays the data after sorting the scores and
               calculating the average */
            displayResults(testScores, averageScore, numScores);
         }
         break;

         case QUIT:
         {
            cout << "\n\tDoing a little housekeeping ... ";

            /* Free up memory */
            delete[] testScores;
            testScores = nullptr;

            cout << "\n\ttestScores cleared: " << testScores
                 << "\n\tPress enter to close this window!\n";
         }
         break;
      }
   } while (menuItem != QUIT); 
}

/* **********************************************************
   Definition: displayMenuItems

   This function displays the menu items the user can select
   between.
   ********************************************************** */

void displayMenuItems()
{
   cout << "\n\n\t\tAVERAGE TEST SCORE CALCULATOR\n\n"
        << "\t1. View Introduction\n"
        << "\t2. Enter Test-Scores\n"
        << "\t3. View Score-Data\n"
        << "\t4. Quit\n\n"
        << "\tYour choice: ";
}

/* **********************************************************
   Definition: displayIntroduction

   This function introduces the program and how it works to
   the user.
   ********************************************************** */

void displayIntro()
{
   cout << "\n\n\t\tAVERAGE TEST SCORE CALCULATOR\n\n"
        << "\tThis program allows you to enter a number of scores to\n"
        << "\tbe averaged. The number of scores to be entered has to\n"
        << "\tbe at least 3.\n\n"
        << "\tAfter the scores have been sorted in ascending order, the\n"
        << "\tthe lowest of all scores is dropped, and the average score\n"
        << "\twill be calculated. Having finished entering your scores,\n"
        << "\tyou can choose option '3' in the menu to view the scores in\n"
        << "\tsorted order and the average score that has been calculated.\n\n";
}

/* **********************************************************
   Definition: getTestScores

   This function accepts testScores and numScores, containing
   the number of elements to be stored in the array, as its
   arguments. It gets the scores to be stored by way of input
   from the user.
   ********************************************************** */

void getTestScores(double *testScores, const int numScores)
{
      for (int index = 0; index < numScores; index++)
      {
         cout << "\tScore #" << (index + 1) << ": ";
         cin >> *(testScores + index);

         /* Validate Input */
         while ((*(testScores + index) <= 0) ||
                (*(testScores + index) > 100.0))
         {
            cout << "\n\t\tYou entered an invalid score!\n\n";
            cout << "\tScore #" << (index + 1) << ": ";
            cin >> *(testScores + index);
         }
      }
      cout << "\n";
}

/* **********************************************************
   Definition: dropLowestScore

   This function accepts testScores and numScores as its
   arguments, containing the number of elements in the array.
   It drops the lowest score and returns the new number of
   elements indicated by numScores. The fact that the lowest
   score is already placed at subscript position 0 after
   sorting is used to advantage here.
   ********************************************************** */

int dropLowestScore(double *testScores, int numScores)
{
   int index = 0;

   numScores--;
   *(testScores + index) = *(testScores + numScores);

   return numScores;
}

/* **********************************************************
   Definition: sortScores

   This function accepts testScores and numScores, containing
   the number of elements stored in the array, as arguments.
   An ascending-order selection sort is performed on the
   elements stored in the array.
   ********************************************************** */

void sortScores(double *testScores, const int numScores)
{
   int startScan = 0,
       minIndex = 0,
       index = 0;

   double minElem = 0.0;

   for (startScan = 0; startScan < (numScores - 1); startScan++)
   {
      minIndex = startScan;
      minElem = *(testScores + startScan);

      for (index = startScan + 1; index < numScores; index++)
      {
         if (*(testScores + index) < minElem)
         {
            minElem = *(testScores + index);
            minIndex = index;
         }
      }

      *(testScores + minIndex) = *(testScores + startScan);
      *(testScores + startScan) = minElem;
   }
}

/* **********************************************************
   Definition: calcAverage

   This function accepts testScores and numScores as its
   argument. It steps through the array to total the scores,
   then calculates and returns the average.
   ********************************************************** */

double calcAverage(double *testScores, const int numScores)
{
   double total = 0.0,
          average = 0.0;

   for (int count = 0; count < numScores; count++)
   {
      total += *(testScores + count);
   }

   /* Calculates and returns the average */
   return average = total / numScores;
}

/* **********************************************************
   Definition: displayResults

   This function accepts testScores, averageScore and
   numScores as its argument. It displays the scores in
   sorted order and the average score.
   ********************************************************** */

void displayResults(const double *testScores, const double averageScore,
                    const int numScores)
{
   int index = 0;

   cout << fixed << showpoint << setprecision(2);

   cout << "\n\n\tTHE SCORES IN SORTED ORDER\n";

      for (index = 0; index < numScores; index++)
      {
         cout << "\n\t\tSCORE #" << (index + 1) << ":\t"
              << setw(5) << right << *(testScores + index)
              << " ";
      }
      cout << "\n\t-------------\n"
           << "\tAVERAGE SCORE:\t\t" << averageScore << "\n";
}

Example Output:





Monday, March 13, 2017

Programming Challenge 9.2 - Test Scores #1

/* Test Scores #1 - This program dynamically allocates an array large
   enough to hold a user-defined number of test scores. Once all scores
   are entered, the array is passed to a function that sorts them in
   ascending order.

   Another function is called that calculates the average score. The
   program displays the sorted list of scores and averages with
   appropriate headings. Pointer notation is used rather than array
   notation whenever possible.

   Input Validation: No negative numbers for test scores is accepted. */

#include "Utility.h"

/* Function prototypes */
void mainMenu();
void displayMenuItems();
void getTestScores(double *, const int);
void sortScores(double *, const int);
double calcAverage(double *, const int);
void displayResults(const double *, const double, const int);

int main()
{
   mainMenu();

   pauseSystem();
   return 0;
}

/* **********************************************************
   Definition: mainMenu

   Allows the user to select from the following items:

      * Enter Test-Score
      * View Score-Data
      * Quit

   It takes care of calling the necessary functions, passing
   and receiving results, and freeing up the memory when the
   user decides to quit the program.
   ********************************************************** */

void mainMenu()
{
   /* Dynamically allocated array */
   double *testScores = nullptr;

   const int GET_TEST_SCORES = 1,
                 VIEW_RESULTS = 2,
                 QUIT = 3;

   int menuItem = 0,
       numScores = 0;

   double averageScore = 0.0;

   do
   {
      displayMenuItems();
      cin >> menuItem;

      /* Validate input */
      while (menuItem < GET_TEST_SCORES || menuItem > QUIT)
      {
         cout << "\n\tInvalid menu item selected!\n"
              << "\tYour choice: ";
         cin >> menuItem;
      }

      switch (menuItem)
      {
         case GET_TEST_SCORES:
         {
            /* Get the number of scores */
            cout << "\n\tHow many test-scores do you wish to enter? ";
            cin >> numScores;
            cout << "\n";

            /* Dynamically allocates the array to hold the number of
               test scores the user wishes to enter */
            testScores = new double[numScores];

            /* Gets the number of scores entered by the user */
            getTestScores(testScores, numScores);

            /* Sorts the scores with an ascending-order selection sort
               algorithm */
            sortScores(testScores, numScores);

            /* Calculates the average score and returns the result */
            averageScore = calcAverage(testScores, numScores);
         }
         break;

         case VIEW_RESULTS:
         {
            /* Displays the data after sorting the scores and
               calculating the average */
            displayResults(testScores, averageScore, numScores);
         }
         break;

         case QUIT:
         {
            cout << "\n\tDoing a little housekeeping ... ";

            /* Free up memory */
            delete[] testScores;
            testScores = nullptr;

            cout << "\n\ttestScores cleared: " << testScores
                 << "\n\tPress enter to close this window!\n";
         }
         break;
      }
   } while (menuItem != QUIT); 
}

/* **********************************************************
   Definition: displayMenuItems

   This function displays the menu items the user can select
   between.
   ********************************************************** */

void displayMenuItems()
{
   cout << "\n\n\t\tAVERAGE TEST SCORE CALCULATOR\n\n"
        << "\t1. Enter Test-Scores\n"
        << "\t2. View Score-Data\n"
        << "\t3. Quit\n\n"
        << "\tYour choice: ";
}

/* **********************************************************
   Definition: getTestScores

   This function accepts testScores and numScores, containing
   the number of elements to be stored in the array, as its
   arguments. It gets the scores to be stored by way of input
   from the user.
   ********************************************************** */

void getTestScores(double *testScores, const int numScores)
{
      for (int index = 0; index < numScores; index++)
      {
         cout << "\tScore #" << (index + 1) << ": ";
         cin >> *(testScores + index);

         /* Validate Input */
         while ((*(testScores + index) <= 0) ||
                (*(testScores + index) > 100.0))
         {
            cout << "\n\t\tYou entered an invalid score!\n\n";
            cout << "\tScore #" << (index + 1) << ": ";
            cin >> *(testScores + index);
         }
      }
      cout << "\n";
}

/* **********************************************************
   Definition: sortScores

   This function accepts testScores and numScores, containing
   the number of elements stored in the array, as arguments.
   An ascending-order selection sort is performed on the
   elements stored in the array.
   ********************************************************** */

void sortScores(double *testScores, const int numScores)
{
   int startScan = 0,
       minIndex = 0,
       index = 0;

   double minElem = 0.0;

   for (startScan = 0; startScan < (numScores - 1); startScan++)
   {
      minIndex = startScan;
      minElem = *(testScores + startScan);

      for (index = startScan + 1; index < numScores; index++)
      {
         if (*(testScores + index) < minElem)
         {
            minElem = *(testScores + index);
            minIndex = index;
         }
      }

      *(testScores + minIndex) = *(testScores + startScan);
      *(testScores + startScan) = minElem;
   }
}

/* **********************************************************
   Definition: calcAverage

   This function accepts testScores and numScores as its
   argument. It steps through the array to total the scores,
   then calculates and returns the average.
   ********************************************************** */

double calcAverage(double *testScores, int numScores)
{
   double total = 0.0,
          average = 0.0;

   for (int count = 0; count < numScores; count++)
   {
      total += *(testScores + count);
   }

   /* Calculates and returns the average */
   return average = total / numScores;
}

/* **********************************************************
   Definition: displayResults

   This function accepts testScores, averageScore and
   numScores as its argument. It displays the scores in
   sorted order and the average score.
   ********************************************************** */

void displayResults(const double *testScores, const double averageScore,
                    const int numScores)
{
   int index = 0;

   cout << fixed << showpoint << setprecision(2);

   cout << "\n\n\tTHE SCORES IN SORTED ORDER\n";

      for (index = 0; index < numScores; index++)
      {
         cout << "\n\t\tSCORE #" << (index + 1) << ":\t"
              << setw(5) << right << *(testScores + index)
              << " ";
      }
      cout << "\n\t-------------\n"
           << "\tAVERAGE SCORE:\t\t" << averageScore << "\n";
}

Example Output:






Sunday, March 12, 2017

Programming Challenge 9.1 - Array Allocator

/* Array Allocator - This program uses a function that dynamically
   allocates an array of integers. The function accepts an integer
   argument indicating the number of elements to allocate. The
   function returns a pointer to the array. */

#include "Utility.h"

/* Function prototypes */
int getNumber();
int *dynamicArray(int);
void displayNumbers(const int[], int);


int main()
{
   /* Points to rndNumbers */
   int *rndNumbers = nullptr;
  
   int numels = 0;

   /* Get the number of elements from the user */
   numels = getNumber();

   /* Gets an array filled with random numbers */
   rndNumbers = dynamicArray(numels);

   /* Display the numbers */
   displayNumbers(rndNumbers, numels);

   /* Free the memory */
   delete [] rndNumbers;
   rndNumbers = nullptr;  

   pauseSystem();
   return 0;
}

/* **********************************************************
   Definition: getNumber

   This function asks the user for the number of elements he
   or she wishes to be contained in rndNumbers.
   ********************************************************** */

int getNumber()
{
   int numels = 0;

   cout << "\n\t\tArray Allocator\n\n"
        << "\tPlease enter the number of elements you wish your array to\n"
        << "\tcontain. After accepting your choice, I will call a function\n"
        << "\tthat dynamically allocates an array to be filled with that\n"
        << "\tamount of random numbers.\n\n"
        << "\tNumber of elements: ";
   cin >> numels;

   return numels;
}

/* **********************************************************
   Definition: dynamicArray

   This function dynamically allocates an array of integers
   being filled with random numbers. The function returns a
   pointer to this array. numbers passed to this function as
   an argument contains the number of elements the user has
   requested.
   ********************************************************** */

int *dynamicArray(int numels)
{
   /* Array containing the randomly generated numbers */
   int *rndNumbers = nullptr;

   /* Returns a null pointer if numels is 0 or negative */
   if (numels <= 0)
   {
      return nullptr;
   }

   /* Dynamically allocate the array */
   rndNumbers = new int[numels];

   /* Seeding the random number generator */
   srand((unsigned int) time(NULL));

   /* Fill the array with random numbers */
   for (int index = 0; index < numels; index++)
   {
      rndNumbers[index] = rand();
   }
  
   /* Returns a pointer to the array */
   return rndNumbers;
}

/* **********************************************************
   Definition: displayNumbers

   This function accepts rndNumbers and numels containing the
   number of elements stored in the array as arguments. It
   displays the randomly generated numbers.
   ********************************************************** */

void displayNumbers(const int rndNumbers[], int numels)
{
   cout << "\n\tAnd here are the numbers I have generated for you:\n\n";

   for (int count = 0; count < numels; count++)
   {
      cout << "\t" << rndNumbers[count] << " \n";
   }
}

Example Output:





Friday, March 10, 2017

Bits and Pieces

(Picture Copyright: My own work)


I can hardly believe that after a mere five days another chapter's challenges are finished! This last Sunday I speculated that by today the first challenge code would go live. I wasn't too sure how the chapter to come would turn out in terms of difficulty. When I started with it, not all of the searching and sorting concepts introduced made sense at first sight. For instance this:

do
   {
      swap = false;

      for (int count = 0; count < (SORT_NUMELS - 1); count++)
      {
         if (bubbleSort[count] > bubbleSort[count + 1])
         {
            temp = bubbleSort[count];
            bubbleSort[count] = bubbleSort[count + 1];
            bubbleSort[count + 1] = temp;

            ++swapCount;

            swap = true;
         }
      }
   } while (swap);

What is actually exchanged when the numbers are sorted? Yes, it is explained in the book, and thoroughly so, but it makes all the difference in the world to read about a concept, writing off the listing in the books, and actually running the code through the debugger to see what happens during execution. By adding parts of the code to watch, things became a little clearer, but still I felt that I didn't fully grasp it. Being very short a chapter, the challenges were soon to come, and after getting my feet wet, I noticed how easy it is to work with searching and sorting algorithms. 

If there was one challenge I felt was difficult then it had to be the one keeping track of the number of swaps. It wasn't the task of writing the code that was difficult, I mean, how difficult can it be to add a counter in a certain place, that takes care of counting the number of swaps? No, the problem there was: How can I verify the number output to screen is correct? What is very easy with selection sort, even past a certain number of elements, proofs to be rather difficult with bubble sort. There are many factors deciding how many swaps are taking place - one among many is the unsorted list. Are certain numbers in certain places already? 

Suffice to say that the web wasn't very helpful in finding an answer to the above question. Not that I didn't learn anything when trying to find one, though. Big-O, Omega and Theta notation, having to do with worst-case time complexity of an algorithm. Or a formula like the following:

(n1)+(n2)+(n3)++3+2+1=n(n1)2=O(n2)

Having to do with the total number of comparisons taking place. I even watched some MIT Lectures hoping to find some answer. They were great but also not the answer to what I was looking for. I eventually found it in a book called The Algorithm Design Manual provided by Penn State University. Not only offers this book past what the title suggests some insights into searching and sorting, proofs and the like, but also this: "The moral of logarithmic growth is clear: If you are gonna do the crime, make it worth the time!". Eventually I found the sought after answer in part in this book as well as on a very dated website that has bubbled down to the depths of my bottomless number of visited websites. This challenge off the table, the other challenges following this one were again very easy. 

What I learned in this lesson is to what good use sorting algorithms can be put when it comes to writing a game. I think with the things learned in this lesson it should be very well possible to write a Tower of Hanoi clone. Besides that the most important lesson learned is the importance of not only giving variables meaningful names, but also how helpful staying consistent with using them can be. My returning visitors will probably know what I mean. For instance having a variable with the name girlNames in place inside main, using this name when calling a function, but in the function header, all of a sudden, girlNames would become something very different. After typing down one of the first code examples this became clear to me. The reason as far as I can tell is that I paid more attention to what was going on in my IDE than seemingly I did in the past. When calling a function, there was also always a little window showing the function prototype: functionName(string[], int, int), being replaced by typing in variable names defined in main. I wonder why I never consciously noticed this, maybe just because it always was there and didn't seem very important. It was almost like a revelation and certainly a step in the right direction. It is like forming a unity between different parts of code by naming things in a certain way so that everything fits together. 

This not only helped in the planning stage before starting to write any code. It also enabled me to write the code faster than it was the case in the past. I think this new understanding is reflected in the code written for all of this chapters challenges. A change - hopefully for the better, has also taken place. I drastically cut down the source-code comments. Sad to say that I managed to incorporate so many that they practically loose their meaning. Another thing I should have noticed and paid more attention to in the past. What good does it do in terms of understanding to have a list of variable names above the variables - telling you that this variable is a counter, and that other one an accumulator? Thinking about it while writing this really makes me laugh. On the the other hand I feel that I owe all of my visitors who read any of my old code an honest apology ... 

S-O-R-R-Y!               ごめんなさい!           Je suis vraiment désolé...            мне очень, очень жаль!

Anyway, I hope you still find some use past the trouble of weeding out all the unnecessary comments when deciding to use any of it for your own projects! That said, it is time to move on, past any mistakes - let bygones be bygones. What is important is what is to come. For me it is chapter 9 and the topic of pointers, which I can only hope will be as easy as this chapter has been. 

I wish my fellow learners will also be blessed with important insights while working on their challenges, overcoming their past mistakes, so they be able to improve. Those kind souls who gave my listings +'s, thank you very much! And to all my visitors, past, present and future, have a nice relaxing weekend. See you all soon, with more code, and myself being one step closer in reaching my ultimate goal!