C++ help with a problem-structs this time

Last Edited By Krjb Donovan
Last Updated: Mar 11, 2014 07:51 PM GMT

Question

Hi I am back with the second go round with this problem-this time including structs and strings. I have done what I can with the info/assignment and now I am stuck. I appreciate your time and help!Thanks

DIRECTIONS:

OBJECTIVE: Compute a student's percentage grade and then assign the appropriate letter grade. Perform the computations for up to 30 students and produce a report ( to a file ) in the format shown in the sample below. (THIS WAS LAB 2 ASSIGNMENT. LAB THREE CONTINUES BELOW This time use an array of structs to hold the student data. Add features to allow reports to be generated to the screen or file that sort by Name or by Percent Grade

-INCLUDE ABOVE MAIN:

Struct student Char FirstName[15]; char LastName[20]; float PercentGrade; char LetterGrade;

-Make sure to have the name broke into two name fields first, and last.

-typedef struct student STUDENT

-use case statements

-create menu such as:

  Grade Machine

1. Enter Students 2. Display By Name to Screen 3. Display By GPA to Screen 4. Write By Name to File 5. Write By GPA to File 0. Exit

-Call in pairs, 1 to call, and 1 to reorder

INPUT:

Student Name 8 labs 3 exams 1 final

COMPUTATIONS:

The percentage grade is equal to the sum of:

-- the average of 8 labs with a 40% weight
-- the average of 3 exams with a 40% weight
-- the final exam with a 20% weight

LOGIC: 94-100 A 85-93 B 75-84 C 65-74 D BELOW 65 F

OUTPUT:

                       GRADE REPORT

NAME  % GRADE LETTER GRADE

Jim Dandy 93 B Sally Sue 78 C Handay Andy 59 F


      • THIS IS WHAT I HAVE SO FAR****
  1. include<stdio.h>
  2. include<stdlib.h>
  3. define _CRT_SECURE_NO_WARNINGS

typedef struct STUDENT {

 char FirstName[15];
 char LastName[20];
 float PercentGrade;
 char LetterGrade;

}STUDENT;

//typedef struct student STUDENT;

  1. define MAX 7

void writeStudents(void); void displayArray(STUDENT []); void sortStudentsByFirstName(STUDENT []); void sortStudentsByLastName(STUDENT []); void sortStudentsByPercentGrade(STUDENT []); void sortStudentsByLetterGrade(STUDENT []);

void enterStudents(void);

main() { int choice;

do {

   printf("\n\n\n Enter Students or 0 to exit\n\n");
   printf("\n  1. Display By Name To Screen");
   printf("\n  2. Display By GPA To Screen");
   printf("\n  3. Write By Name To File");

printf("\n 4. Write By GPA To File");

   printf("\n\n  Enter you selection ==> :");
   fflush(stdin);
   scanf("%d", &choice);

switch(choice)

   {
   
     case 1 : printf("\nDisplay By Name");  
              break; 
     case 2 : printf("\nDisplay By GPA"); 
              break;
     case 3 : printf("\nWrite By Name"); 
              break;
     case 4 : printf("\nWrite By GPA"); 
              break;
     case 0 : break;
     default: printf("\nYour options are 0-4");
              printf("\nPress <Enter> to try again");
              fflush(stdin);
              getchar();
   }
 } while(choice);

 return(0);

} void enterStudents(void) { printf("\nDisplay By Name");

     printf("\nDisplay By GPA"); 
     printf("\nWrite By Name"); 
     printf("\nWrite By GPA"); 

}

  STUDENT mixed[15];
  int i;
  FILE * fptr;
  writeStudents();
  fptr = fopen("Students.dat", "rb");
  if(fptr ==NULL)

{ printf("\n Grade Report Today!"); fflush(stdin);getchar(); exit(0); }

  i=0;
  
  fread(&mixed[i],sizeof(STUDENT), 1, fptr);
  while(!feof(fptr))
  {

printf("\n %s", mixed[i].FirstName); i++; fread(&mixed[i], sizeof(STUDENT), 1, fptr);

      printf("\n %s", mixed[i].LastName);

i++; fread(&mixed[i], sizeof(STUDENT), 1, fptr);

printf("\n %s", mixed[i].PercentGrade); i++; fread(&mixed[i], sizeof(STUDENT), 1, fptr);

      printf("\n %s", mixed[i].PercentGrade);

i++; fread(&mixed[i], sizeof(STUDENT), 1, fptr);

  }
  fclose(fptr);
return(0);

}

void writeStudents(void) { STUDENT mixed[MAX]= { {"Tom", "Thumb", 105.00, '*'}, {"Jim", "Bean", 95.00, 'A'}, {"Sippy", "Cup", 85.00, 'B'}, {"Green", "Giant", 75.00, 'C'}, {"Dead", "Aunt", 65.00, 'D'}, {"Speed", "Racer", 55.00, 'F'},

                               {"Hide", "NSeek", -10.00, '*'},

}; FILE * fptr; int i;

fptr = fopen("Students.dat", "wb"); if(fptr == NULL) { priintf("\n Grade Report Today!"); fflush(stdin);getchar(); exit(0); }

     for(i=0; i<MAX; i++)

{ fwrite(&mixed[i], sizeof(STUDENT),1, fptr); }

     displayArray(mixed);
     sortStudentsByFirstName(mixed);
     sortStudentsByLastName(mixed);
     sortStudentsByPercentGrade(mixed);
     sortStudentsByLetterGrade(mixed);
   displayArray(mixed);
   fclose(fptr);

} void displayArray(STUDENT mixed[]) {

 int i;
 for(i=0; i<MAX; i++)
 {
   printf("\n %s %.2f %c", mixed[i].FirstName,mixed[i].LastName,mixed[i].PercentGrade,mixed[i].LetterGrade);
 }
 printf("\n");


} void sortStudentsByFirstName(STUDENT mixed[]) { STUDENT temp; int i; int x;

for(x-0; x < MAX-1; x++) { for(i=0; i < MAX-1-x; i++) { if( strcmp(mixed[i].FirstName, mixed[i+1].FirstName)> 0) { temp = mixed[i]; mixed[i] = mixed[i+1]; mixed[i+1] = temp; } } } }


void sortStudentsByLastName(STUDENT mixed[]) { STUDENT temp; int i; int x;

for(x-0; x < MAX-1; x++) { for(i=0; i < MAX-1-x; i++) { if( strcmp(mixed[i].LastName, mixed[i+1].LastName)> 0) { temp = mixed[i]; mixed[i] = mixed[i+1]; mixed[i+1] = temp; } } } }

void sortStudentsByPercentGrade(STUDENT mixed[]) { STUDENT temp; int i; int x;

for(x-0; x < MAX-1; x++) { for(i=0; i < MAX-1-x; i++) { if(mixed[i].PercentGrade > mixed[i+1].PercentGrade) { temp = mixed[i]; mixed[i] = mixed[i+1]; mixed[i+1] = temp; } } } }

void sortStudentsByLetterGrade(STUDENT mixed[]) { STUDENT temp; int i; int x;

for(x-0; x < MAX-1; x++) { for(i=0; i < MAX-1-x; i++) { if(mixed[i].LetterGrade > mixed[i+1].LetterGrade) { temp = mixed[i]; mixed[i] = mixed[i+1]; mixed[i+1] = temp; } } } }


/*float calcPercentGrade(void) *** DO I NEED THIS AND THE BELOW INFORMATION STILL IN THE PROGRAM??? {

/* float percentGrade;
 float labs;
 float exams;
 float final;

  labs = calcLabs();

  exams = calcExams();
 
  final = calcFinal();
 
  percentGrade = labs + exams + final;
 return percentGrade;*
 return calcLabs() + calcExams() + calcFinal();

} float calcLabs(void) {

  float labs = 0;
  float oneLab;
  int i;
  for(i =0; i<NUMBER_OF_LABS; i++)
  {
     printf("\nEnter lab %d: ", i+1);
     fflush(stdin);
     scanf("%f", &oneLab);
     labs=oneLab;
  }
   labs = (labs/NUMBER_OF_LABS)*0.40f;
  return labs;

} float calcExams(void) {

  float exams = 0;
  float oneExam;
  int i;
  for(i =0; i<NUMBER_OF_EXAMS; i++)
  {
     printf("\nEnter Exams %d: ", i+1);
     fflush(stdin);
     scanf("%f", &oneExam);
     exams+=oneExam;
  }
   exams = (exams/NUMBER_OF_EXAMS)*0.40f;
  return exams;

} float calcFinal(void) {

 float final;
 printf("\nEnter Final: ");
 fflush(stdin);
 scanf("%f", &final);
 final = final *0.20f;
 return final;

} char calcLetterGrade(float percentGrade) {

/* char letterGrade = 'X';
 if(percentGrade > 100 || percentGrade < 0)
 {
    letterGrade = '*';
 }
 else
 {

if(percentGrade >= 94) {

     letterGrade = 'A';

} else {

     if(percentGrade >= 84)

{

       letterGrade = 'B';

} else {

       if(percentGrade >= 74)

{

          letterGrade = 'C';

} else {

         if(percentGrade >= 65)

{

            letterGrade = 'D';

} else {

            letterGrade = 'F';

} } } }

 }
 return letterGrade;

if(percentGrade > 100 || percentGrade < 0)

 {
    return '*';
 }
 else
 {

if(percentGrade >= 94) {

      return 'A';

} else {

     if(percentGrade >= 84)

{

       return 'B';

} else {

       if(percentGrade >= 74)

{

          return  'C';

} else {

         if(percentGrade >= 65)

{

            return 'D';

} else {

            return 'F';

} } } }

 }
 return 'X';

}

  • /

Answer

Hello Shannon.

I think you make a good start on your program, but some parts were incomplete and did not compile. You did a good job on the sort routines, but you seem to have trouble with input. I've done what I can to give you a working program. The program does not do everything that the assignment asks for. Have a look at my program, and read the comments in it. Then make changes so that it does what you need.

I made the enterStudents function read from the keyboard. It was not clear to me if input should come from the keyboard, or a file, or both.

The writeStudents function still needs to be done.

  1. include<stdio.h>
  2. include<stdlib.h>
  3. include<string.h>
  4. include<ctype.h>
  5. define _CRT_SECURE_NO_WARNINGS

typedef struct STUDENT {

   char FirstName[15];
   char LastName[20];
   float PercentGrade;
   char LetterGrade;

}STUDENT;


/* declare students here. This array will hold your students. MAX is the maximum number allowed, but you may have less. Use the variable studentCount for the actual number of students

  • /
  1. define MAX 7

int studentCount = 0; STUDENT students[MAX];

void writeStudents(void); void displayArray(STUDENT []); void sortStudentsByFirstName(STUDENT []); void sortStudentsByLastName(STUDENT []); void sortStudentsByPercentGrade(STUDENT []); void sortStudentsByLetterGrade(STUDENT []);

void enterStudents(void);

int main() {

   int choice;
   do
   {
       /* The assignment instruction said the menu is like this:
       1. Enter Students
       2. Display By Name to Screen
       3. Display By GPA to Screen
       4. Write By Name to File
       5. Write By GPA to File
       0. Exit
       */
       printf("\n\n\n Enter Students or 0 to exit\n\n");
       printf("\n  1. Enter Students");
       printf("\n  2. Display By Name To Screen");
       printf("\n  3. Display By GPA To Screen");
       printf("\n  4. Write By Name To File");
       printf("\n  5. Write By GPA To File");
       printf("\n  0. Exit");
       printf("\n\n  Enter you selection ==> :");
       //get input and check that input succeeded
       fflush(stdin);
       if (scanf("%d", &choice) == 1)
       {
           /*
           From the different cases, call the function or set of functions that
           will complete the operation. I am a little unclear about these operations but
           I assume for example that display by name means sort by last name then display 
           to the screen. I assume GPA is like the percent grade. Is that correct ??
           */
           switch(choice)
           {
           case 1 : 
               enterStudents();
               break;
           case 2 : 
               sortStudentsByLastName(students);
               displayArray(students);
               break;
           case 3 :
               sortStudentsByPercentGrade(students);
               displayArray(students);
               break;
           case 4 : 
               sortStudentsByLastName(students);
               writeStudents();
               break;
           case 5:
               sortStudentsByPercentGrade(students);
               writeStudents();
               break;
           case 0 : break;
           default: 
               printf("\nYour options are 0-4");
               printf("\nPress <Enter> to try again\n");
               break;
           }
       }
       else
       {
           printf("\nYour options are 0-4");
           printf("\nPress <Enter> to try again\n");
           // scanf failed, but we want the choice loop to keep going
           choice = -1; 
       }
   } while(choice);
   return(0);

}

/* There was a lot of code here not inside of any function Code not inside a function will not compile. It seemed to be a mixture of ideas, some reading from keyboard, some from the file. I got rid of the file stuff. You can create a readStudentsFromFile function if you like

  • /

/* Function enterStudents This function reads students from the keyboard An effort is made to ensure that all input is valid, and that no buffers overflow.

  • /

void enterStudents(void) {

   studentCount = 0;
   //Don't overflow array
   while(studentCount < MAX)
   {
       // Each student field is read within a loop to allow error checking.
       while(1)
       {
           printf("First name :");
           /* I am using scanf_s to ensure there is no buffer overflow */
           fflush(stdin);
           if (scanf_s("%s", students[studentCount].FirstName, sizeof(students[studentCount].FirstName)) == 1)
           {
               break; // good input, get out of the name loop
           }
           else
           {
               printf("No, that's not a valid first name\n");
           }
       }
       while(1)
       {
           printf("Last name :");
           fflush(stdin);
           if (scanf_s("%s", students[studentCount].LastName, sizeof(students[studentCount].LastName)) == 1)
           {
               break; // good input, get out of the name loop
           }
           else
           {
               printf("No, that's not a valid last name\n");
           }
       }
       while(1)
       {
           printf("Percent grade :");
           fflush(stdin);
           if (scanf("%f", &students[studentCount].PercentGrade) == 1
               && students[studentCount].PercentGrade >= 0
               &&  students[studentCount].PercentGrade <= 100)
           {
               break; // good input, get out of the grade loop
           }
           else
           {
               printf("No, that's not a valid percent grade\n");
           }
       }
       // Letter grades are ABCD and F ??
       while(1)
       {
           printf("Letter grade :");
           fflush(stdin);
           scanf("%c", &students[studentCount].LetterGrade);
           students[studentCount].LetterGrade = toupper(students[studentCount].LetterGrade);
           if (students[studentCount].LetterGrade >= 'A' && students[studentCount].LetterGrade <= 'D' ||
               students[studentCount].LetterGrade == 'F')
           {
               break;// good input, get out of the grade loop
           }
           else
           {
               printf("No, that's not a valid letter grade\n");
           }
       }
       printf("This student '%s/%s' %f %c\n", 
           students[studentCount].FirstName, students[studentCount].LastName, students[studentCount].PercentGrade, students[studentCount].LetterGrade);
       //Finally, increment the studentCount
       ++studentCount;
       // if there is more room, allow for more students to be input
       if (studentCount < MAX)
       {
           printf("Enter another student ?");
           fflush(stdin);
           if (toupper(getchar()) != 'Y') break;
       }
   }

}

/* This function should write students to a file. It does not need to do any sorting.

  • /

void writeStudents(void) {

   //FILE * fptr;
   //int i;
   //fptr = fopen("Students.dat", "wb");
   //if(fptr == NULL)
   //{
   //    printf("\n Grade Report Today!");
   //    fflush(stdin);getchar();
   //    exit(0);
   //}
   //for(i=0; i<MAX; i++)
   //{
   //    fwrite(&mixed[i], sizeof(STUDENT),1, fptr);
   //}
   //displayArray(mixed);
   //sortStudentsByFirstName(mixed);
   //sortStudentsByLastName(mixed);
   //sortStudentsByPercentGrade(mixed);
   //sortStudentsByLetterGrade(mixed);
   //displayArray(mixed);
   //fclose(fptr);

}

void displayArray(STUDENT mixed[]) {

   int i;
   for(i=0; i<studentCount; i++)
   {
       printf("'%s/%s' %f %c\n", mixed[i].FirstName,mixed[i].LastName,mixed[i].PercentGrade,mixed[i].LetterGrade);
   }

}

/* These sort functions look good, but use studentCount, instead of MAX */

void sortStudentsByFirstName(STUDENT mixed[]) {

   STUDENT temp;
   int i;
   int x;
   for(x=0; x < studentCount-1; x++)
   {
       for(i=0; i < studentCount-1-x; i++)
       {
           if( strcmp(mixed[i].FirstName, mixed[i+1].FirstName)> 0)
           {
               temp = mixed[i];
               mixed[i] = mixed[i+1];
               mixed[i+1] = temp;
           }
       }
   }

}


void sortStudentsByLastName(STUDENT mixed[]) {

   STUDENT temp;
   int i;
   int x;
   for(x=0; x < studentCount-1; x++)
   {
       for(i=0; i < studentCount-1-x; i++)
       {
           if( strcmp(mixed[i].LastName, mixed[i+1].LastName)> 0)
           {
               temp = mixed[i];
               mixed[i] = mixed[i+1];
               mixed[i+1] = temp;
           }
       }
   }

}

void sortStudentsByPercentGrade(STUDENT mixed[]) {

   STUDENT temp;
   int i;
   int x;
   for(x=0; x < studentCount-1; x++)
   {
       for(i=0; i < studentCount-1-x; i++)
       {
           if(mixed[i].PercentGrade > mixed[i+1].PercentGrade)
           {
               temp = mixed[i];
               mixed[i] = mixed[i+1];
               mixed[i+1] = temp;
           }
       }
   }

}

void sortStudentsByLetterGrade(STUDENT mixed[]) {

   STUDENT temp;
   int i;
   int x;
   for(x=0; x < studentCount-1; x++)
   {
       for(i=0; i < studentCount-1-x; i++)
       {
           if(mixed[i].LetterGrade > mixed[i+1].LetterGrade)
           {
               temp = mixed[i];
               mixed[i] = mixed[i+1];
               mixed[i+1] = temp;
           }
       }
   }

}

Advertisement

©2021 eLuminary LLC. All rights reserved.