Arrays

Last Edited By Krjb Donovan
Last Updated: Mar 12, 2014 02:46 PM GMT

QuestionEdit

  1. include <iostream>
  2. include <iomanip>

using namespace std;

const int SIZE = 5, LENGTH = 25, SCORES = 4;

void getNames(char [][LENGTH]); void getScores(char [][LENGTH], char [], double [][SCORES]); void display(char [][LENGTH], char [], double [][SCORES]);

int main() { char students[SIZE][LENGTH]; char grades[SIZE]; double score[SIZE][SCORES];

getNames(students); getScores(students,grades,score); display(students,grades,score);

return 0; }

void getNames(char students[][LENGTH]) { for(int i = 0; i < SIZE; i++) { cout << "Please enter student " << (i+1) << " name: "; cin.getline(students[i],LENGTH); } }

void getScores(char students[][LENGTH], char grade[], double score[][SCORES]) { int avg = 0;

for(int i = 0; i < SIZE; i++) {

for(int j = 0; j < SCORES; j++) { cout << "Please enter " << students[i] << " grade "; cout << (j+1) << ": "; cin >> score[i][j]; avg += score[i][j]; }

avg = avg / SCORES;

if(avg > 89) grade[i] = 'A'; else if(avg > 79) grade[i] = 'B'; else if(avg > 69) grade[i] = 'C'; else if(avg > 59) grade[i] = 'D'; else grade[i] = 'F'; }

}

void display(char s[][LENGTH], char g[], double sc[][SCORES]) { int avg = 0;

for(int i = 0; i < SIZE; i++) { cout << s[i] << endl;

for(int j = 0; j < SCORES; j++) { cout << sc[i][j] << endl; avg += sc[i][j]; }

cout << g[i] << endl; } }


  • Note: the program builds successfully, but how can I clean it up a bit?

AnswerEdit

Hello Dionne.

I think you did a good job on your program.

I'll make some suggestions. You should make your calculated avg a double instead of an int because the score array holds doubles. That will remove a compiler warning, and make your division more precise. In your case, you don't need the extra precision, but personally, I like to have no warnings, and I like my data types to match.

The avg calculation in the display function is not really doing anything. Was it left over from an older version of the program? You should remove it.

There is a lot happening in getScores. The function is called getScores, but it also does calculation. Generally functions should do one thing and be named for that thing. I would have getScores only get the user's input. I would have a calcAverages function called from main to do the calculations. With such a small program, it's hard to see the advantage of a separate function for calculating averages, but that's what I recommend. My first programming instructor told me the same thing. What you have in getScores is an example of "Temporal Cohesion" You are grouping together different operations just because they can be done at the same time. There are many internet definitions of cohesion. You can have a look at http://en.wikipedia.org/wiki/Cohesion_%28computer_science%29

You can read more about what makes a good function from the book "Code Complete". If programming is going to be your career, then you need to read that book. It is written better than most internet articles, and you are sophisticated enough to understand it.

Look at http://cc2e.com/

My last suggestion is that you test your program with bad input. How does it react if you put in letters when it's expecting numbers? What happens if you try to input a name larger than LENGTH? Input is always a tricky thing. When you do cin.getline(students[i],LENGTH); the LENGTH parameter prevents a buffer overflow, but if the user tries to enter more than LENGTH, the extra will be picked up on the next read.

During input I would do:

       string inputLine;
       getline(cin, inputLine);
       // Copy only LENGTH characters to the student name
       strncpy(students[i], inputLine.c_str(), LENGTH); 
       // Optionally, check the inputLine length to make sure it is less than LENGTH
       // and warn the user if it is.
       // Make sure to null terminate the name
       students[i][LENGTH-1] = 0; 

The inputLine object will grow to accommodate the input, then you can check if it is too long. There will be no buffer overflow, and there will be no garbage left in the input buffer.


You say you are confused by arrays, but I don't see any misuse. If you have a particular question, please post a follow-up. Thanks again for the thoughtful question.

Advertisement

©2024 eLuminary LLC. All rights reserved.